<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<!--[if IE]><meta http-equiv="X-UA-Compatible" content="IE=edge"><![endif]-->
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="generator" content="Asciidoctor 1.5.2">
<meta name="author" content="Stephane Maldini, Jon Brisbin">
<title>Reactor Guide</title>
<style>
@import url(https://fonts.googleapis.com/css?family=Varela+Round|Open+Sans:400italic,700italic,400,700);
/*! normalize.css v2.1.2 | MIT License | git.io/normalize */
/* ========================================================================== HTML5 display definitions ========================================================================== */
/** Correct `block` display not defined in IE 8/9. */
@import url(https://cdnjs.cloudflare.com/ajax/libs/font-awesome/3.2.1/css/font-awesome.css);
article, aside, details, figcaption, figure, footer, header, hgroup, main, nav, section, summary { display: block; }

/** Correct `inline-block` display not defined in IE 8/9. */
audio, canvas, video { display: inline-block; }

/** Prevent modern browsers from displaying `audio` without controls. Remove excess height in iOS 5 devices. */
audio:not([controls]) { display: none; height: 0; }

/** Address `[hidden]` styling not present in IE 8/9. Hide the `template` element in IE, Safari, and Firefox < 22. */
[hidden], template { display: none; }

script { display: none !important; }

/* ========================================================================== Base ========================================================================== */
/** 1. Set default font family to sans-serif. 2. Prevent iOS text size adjust after orientation change, without disabling user zoom. */
html { font-family: sans-serif; /* 1 */ -ms-text-size-adjust: 100%; /* 2 */ -webkit-text-size-adjust: 100%; /* 2 */ }

/** Remove default margin. */
body { margin: 0; }

/* ========================================================================== Links ========================================================================== */
/** Remove the gray background color from active links in IE 10. */
a { background: transparent; }

/** Address `outline` inconsistency between Chrome and other browsers. */
a:focus { outline: thin dotted; }

/** Improve readability when focused and also mouse hovered in all browsers. */
a:active, a:hover { outline: 0; }

/* ========================================================================== Typography ========================================================================== */
/** Address variable `h1` font-size and margin within `section` and `article` contexts in Firefox 4+, Safari 5, and Chrome. */
h1 { font-size: 2em; margin: 0.67em 0; }

/** Address styling not present in IE 8/9, Safari 5, and Chrome. */
abbr[title] { border-bottom: 1px dotted; }

/** Address style set to `bolder` in Firefox 4+, Safari 5, and Chrome. */
b, strong { font-weight: bold; }

/** Address styling not present in Safari 5 and Chrome. */
dfn { font-style: italic; }

/** Address differences between Firefox and other browsers. */
hr { -moz-box-sizing: content-box; box-sizing: content-box; height: 0; }

/** Address styling not present in IE 8/9. */
mark { background: #ff0; color: #000; }

/** Correct font family set oddly in Safari 5 and Chrome. */
code, kbd, pre, samp { font-family: monospace, serif; font-size: 1em; }

/** Improve readability of pre-formatted text in all browsers. */
pre { white-space: pre-wrap; }

/** Set consistent quote types. */
q { quotes: "\201C" "\201D" "\2018" "\2019"; }

/** Address inconsistent and variable font size in all browsers. */
small { font-size: 80%; }

/** Prevent `sub` and `sup` affecting `line-height` in all browsers. */
sub, sup { font-size: 75%; line-height: 0; position: relative; vertical-align: baseline; }

sup { top: -0.5em; }

sub { bottom: -0.25em; }

/* ========================================================================== Embedded content ========================================================================== */
/** Remove border when inside `a` element in IE 8/9. */
img { border: 0; }

/** Correct overflow displayed oddly in IE 9. */
svg:not(:root) { overflow: hidden; }

/* ========================================================================== Figures ========================================================================== */
/** Address margin not present in IE 8/9 and Safari 5. */
figure { margin: 0; }

/* ========================================================================== Forms ========================================================================== */
/** Define consistent border, margin, and padding. */
fieldset { border: 1px solid #c0c0c0; margin: 0 2px; padding: 0.35em 0.625em 0.75em; }

/** 1. Correct `color` not being inherited in IE 8/9. 2. Remove padding so people aren't caught out if they zero out fieldsets. */
legend { border: 0; /* 1 */ padding: 0; /* 2 */ }

/** 1. Correct font family not being inherited in all browsers. 2. Correct font size not being inherited in all browsers. 3. Address margins set differently in Firefox 4+, Safari 5, and Chrome. */
button, input, select, textarea { font-family: inherit; /* 1 */ font-size: 100%; /* 2 */ margin: 0; /* 3 */ }

/** Address Firefox 4+ setting `line-height` on `input` using `!important` in the UA stylesheet. */
button, input { line-height: normal; }

/** Address inconsistent `text-transform` inheritance for `button` and `select`. All other form control elements do not inherit `text-transform` values. Correct `button` style inheritance in Chrome, Safari 5+, and IE 8+. Correct `select` style inheritance in Firefox 4+ and Opera. */
button, select { text-transform: none; }

/** 1. Avoid the WebKit bug in Android 4.0.* where (2) destroys native `audio` and `video` controls. 2. Correct inability to style clickable `input` types in iOS. 3. Improve usability and consistency of cursor style between image-type `input` and others. */
button, html input[type="button"], input[type="reset"], input[type="submit"] { -webkit-appearance: button; /* 2 */ cursor: pointer; /* 3 */ }

/** Re-set default cursor for disabled elements. */
button[disabled], html input[disabled] { cursor: default; }

/** 1. Address box sizing set to `content-box` in IE 8/9. 2. Remove excess padding in IE 8/9. */
input[type="checkbox"], input[type="radio"] { box-sizing: border-box; /* 1 */ padding: 0; /* 2 */ }

/** 1. Address `appearance` set to `searchfield` in Safari 5 and Chrome. 2. Address `box-sizing` set to `border-box` in Safari 5 and Chrome (include `-moz` to future-proof). */
input[type="search"] { -webkit-appearance: textfield; /* 1 */ -moz-box-sizing: content-box; -webkit-box-sizing: content-box; /* 2 */ box-sizing: content-box; }

/** Remove inner padding and search cancel button in Safari 5 and Chrome on OS X. */
input[type="search"]::-webkit-search-cancel-button, input[type="search"]::-webkit-search-decoration { -webkit-appearance: none; }

/** Remove inner padding and border in Firefox 4+. */
button::-moz-focus-inner, input::-moz-focus-inner { border: 0; padding: 0; }

/** 1. Remove default vertical scrollbar in IE 8/9. 2. Improve readability and alignment in all browsers. */
textarea { overflow: auto; /* 1 */ vertical-align: top; /* 2 */ }

/* ========================================================================== Tables ========================================================================== */
/** Remove most spacing between table cells. */
table { border-collapse: collapse; border-spacing: 0; }

meta.foundation-mq-small { font-family: "only screen and (min-width: 768px)"; width: 768px; }

meta.foundation-mq-medium { font-family: "only screen and (min-width:1280px)"; width: 1280px; }

meta.foundation-mq-large { font-family: "only screen and (min-width:1440px)"; width: 1440px; }

*, *:before, *:after { -moz-box-sizing: border-box; -webkit-box-sizing: border-box; box-sizing: border-box; }

html, body { font-size: 100%; }

body { background: white; color: #222222; padding: 0; margin: 0; font-family: "Helvetica Neue", "Helvetica", Helvetica, Arial, sans-serif; font-weight: normal; font-style: normal; line-height: 1; position: relative; cursor: auto; }

a:hover { cursor: pointer; }

img, object, embed { max-width: 100%; height: auto; }

object, embed { height: 100%; }

img { -ms-interpolation-mode: bicubic; }

#map_canvas img, #map_canvas embed, #map_canvas object, .map_canvas img, .map_canvas embed, .map_canvas object { max-width: none !important; }

.left { float: left !important; }

.right { float: right !important; }

.text-left { text-align: left !important; }

.text-right { text-align: right !important; }

.text-center { text-align: center !important; }

.text-justify { text-align: justify !important; }

.hide { display: none; }

.antialiased, body { -webkit-font-smoothing: antialiased; }

img { display: inline-block; vertical-align: middle; }

textarea { height: auto; min-height: 50px; }

select { width: 100%; }

p.lead, .paragraph.lead > p, #preamble > .sectionbody > .paragraph:first-of-type p { font-size: 1.21875em; line-height: 1.6; }

.subheader, #content #toctitle, .admonitionblock td.content > .title, .exampleblock > .title, .imageblock > .title, .listingblock > .title, .literalblock > .title, .mathblock > .title, .openblock > .title, .paragraph > .title, .quoteblock > .title, .sidebarblock > .title, .tableblock > .title, .verseblock > .title, .videoblock > .title, .dlist > .title, .olist > .title, .ulist > .title, .qlist > .title, .hdlist > .title, .tableblock > caption { line-height: 1.4; color: #385dbd; font-weight: 300; margin-top: 0.2em; margin-bottom: 0.5em; }

/* Typography resets */
div, dl, dt, dd, ul, ol, li, h1, h2, h3, #toctitle, .sidebarblock > .content > .title, h4, h5, h6, pre, form, p, blockquote, th, td { margin: 0; padding: 0; direction: ltr; }

/* Default Link Styles */
a { color: #095557; text-decoration: underline; line-height: inherit; }
a:hover, a:focus { color: #042829; }
a img { border: none; }

/* Default paragraph styles */
p { font-family: inherit; font-weight: normal; font-size: 1em; line-height: 1.6; margin-bottom: 1.25em; text-rendering: optimizeLegibility; }
p aside { font-size: 0.875em; line-height: 1.35; font-style: italic; }

/* Default header styles */
h1, h2, h3, #toctitle, .sidebarblock > .content > .title, h4, h5, h6 { font-family: "Varela Round", Arial, sans-serif; font-weight: normal; font-style: normal; color: #152347; text-rendering: optimizeLegibility; margin-top: 0.8em; margin-bottom: 0.5em; line-height: 1.2125em; }
h1 small, h2 small, h3 small, #toctitle small, .sidebarblock > .content > .title small, h4 small, h5 small, h6 small { font-size: 60%; color: #385dbd; line-height: 0; }

h1 { font-size: 2.125em; }

h2 { font-size: 1.6875em; }

h3, #toctitle, .sidebarblock > .content > .title { font-size: 1.375em; }

h4 { font-size: 1.125em; }

h5 { font-size: 1.125em; }

h6 { font-size: 1em; }

hr { border: solid #dcd2c9; border-width: 1px 0 0; clear: both; margin: 1.25em 0 1.1875em; height: 0; }

/* Helpful Typography Defaults */
em, i { font-style: italic; line-height: inherit; }

strong, b { font-weight: bold; line-height: inherit; }

small { font-size: 60%; line-height: inherit; }

code { font-family: Consolas, "Liberation Mono", Courier, monospace; font-weight: bold; color: #691816; }

/* Lists */
ul, ol, dl { font-size: 1em; line-height: 1.6; margin-bottom: 1.25em; list-style-position: outside; font-family: inherit; }

ul, ol { margin-left: 1.5em; }
ul.no-bullet, ol.no-bullet { margin-left: 1.5em; }

/* Unordered Lists */
ul li ul, ul li ol { margin-left: 1.25em; margin-bottom: 0; font-size: 1em; /* Override nested font-size change */ }
ul.square li ul, ul.circle li ul, ul.disc li ul { list-style: inherit; }
ul.square { list-style-type: square; }
ul.circle { list-style-type: circle; }
ul.disc { list-style-type: disc; }
ul.no-bullet { list-style: none; }

/* Ordered Lists */
ol li ul, ol li ol { margin-left: 1.25em; margin-bottom: 0; }

/* Definition Lists */
dl dt { margin-bottom: 0.3125em; font-weight: bold; }
dl dd { margin-bottom: 1.25em; }

/* Abbreviations */
abbr, acronym { text-transform: uppercase; font-size: 90%; color: #211306; border-bottom: 1px dotted #dddddd; cursor: help; }

abbr { text-transform: none; }

/* Blockquotes */
blockquote { margin: 0 0 1.25em; padding: 0.5625em 1.25em 0 1.1875em; border-left: 1px solid #dddddd; }
blockquote cite { display: block; font-size: 0.8125em; color: #655241; }
blockquote cite:before { content: "\2014 \0020"; }
blockquote cite a, blockquote cite a:visited { color: #655241; }

blockquote, blockquote p { line-height: 1.6; color: #846b55; }

/* Microformats */
.vcard { display: inline-block; margin: 0 0 1.25em 0; border: 1px solid #dddddd; padding: 0.625em 0.75em; }
.vcard li { margin: 0; display: block; }
.vcard .fn { font-weight: bold; font-size: 0.9375em; }

.vevent .summary { font-weight: bold; }
.vevent abbr { cursor: auto; text-decoration: none; font-weight: bold; border: none; padding: 0 0.0625em; }

@media only screen and (min-width: 768px) { h1, h2, h3, #toctitle, .sidebarblock > .content > .title, h4, h5, h6 { line-height: 1.4; }
  h1 { font-size: 2.75em; }
  h2 { font-size: 2.3125em; }
  h3, #toctitle, .sidebarblock > .content > .title { font-size: 1.6875em; }
  h4 { font-size: 1.4375em; } }
/* Print styles.  Inlined to avoid required HTTP connection: www.phpied.com/delay-loading-your-print-css/ Credit to Paul Irish and HTML5 Boilerplate (html5boilerplate.com)
*/
.print-only { display: none !important; }

@media print { * { background: transparent !important; color: #000 !important; /* Black prints faster: h5bp.com/s */ box-shadow: none !important; text-shadow: none !important; }
  a, a:visited { text-decoration: underline; }
  a[href]:after { content: " (" attr(href) ")"; }
  abbr[title]:after { content: " (" attr(title) ")"; }
  .ir a:after, a[href^="javascript:"]:after, a[href^="#"]:after { content: ""; }
  pre, blockquote { border: 1px solid #999; page-break-inside: avoid; }
  thead { display: table-header-group; /* h5bp.com/t */ }
  tr, img { page-break-inside: avoid; }
  img { max-width: 100% !important; }
  @page { margin: 0.5cm; }
  p, h2, h3, #toctitle, .sidebarblock > .content > .title { orphans: 3; widows: 3; }
  h2, h3, #toctitle, .sidebarblock > .content > .title { page-break-after: avoid; }
  .hide-on-print { display: none !important; }
  .print-only { display: block !important; }
  .hide-for-print { display: none !important; }
  .show-for-print { display: inherit !important; } }
/* Tables */
table { background: white; margin-bottom: 1.25em; border: solid 1px #e4e7ef; }
table thead, table tfoot { background: rgba(105, 60, 22, 0.25); font-weight: bold; }
table thead tr th, table thead tr td, table tfoot tr th, table tfoot tr td { padding: 0.5em 0.625em 0.625em; font-size: inherit; color: #211306; text-align: left; }
table tr th, table tr td { padding: 0.5625em 0.625em; font-size: inherit; color: #211306; }
table tr.even, table tr.alt, table tr:nth-of-type(even) { background: #f4f5f8; }
table thead tr th, table tfoot tr th, table tbody tr td, table tr td, table tfoot tr td { display: table-cell; line-height: 1.6; }

.clearfix:before, .clearfix:after, .float-group:before, .float-group:after { content: " "; display: table; }
.clearfix:after, .float-group:after { clear: both; }

*:not(pre) > code { font-size: inherit; padding: 0; white-space: nowrap; background-color: inherit; border: 0 solid #dddddd; -webkit-border-radius: 6px; border-radius: 6px; text-shadow: none; }

pre, pre > code { line-height: 1.4; color: black; font-family: monospace, serif; font-weight: normal; }

.keyseq { color: #774417; }

kbd:not(.keyseq) { display: inline-block; color: #211306; font-size: 0.75em; line-height: 1.4; background-color: #F7F7F7; border: 1px solid #ccc; -webkit-border-radius: 3px; border-radius: 3px; -webkit-box-shadow: 0 1px 0 rgba(0, 0, 0, 0.2), 0 0 0 2px white inset; box-shadow: 0 1px 0 rgba(0, 0, 0, 0.2), 0 0 0 2px white inset; margin: -0.15em 0.15em 0 0.15em; padding: 0.2em 0.6em 0.2em 0.5em; vertical-align: middle; white-space: nowrap; }

.keyseq kbd:first-child { margin-left: 0; }

.keyseq kbd:last-child { margin-right: 0; }

.menuseq, .menu { color: black; }

b.button:before, b.button:after { position: relative; top: -1px; font-weight: normal; }

b.button:before { content: "["; padding: 0 3px 0 2px; }

b.button:after { content: "]"; padding: 0 2px 0 3px; }

p a > code:hover { color: #541312; }

#header, #content, #footnotes, #footer { width: 100%; margin-left: auto; margin-right: auto; margin-top: 0; margin-bottom: 0; max-width: 62.5em; *zoom: 1; position: relative; padding-left: 0.9375em; padding-right: 0.9375em; }
#header:before, #header:after, #content:before, #content:after, #footnotes:before, #footnotes:after, #footer:before, #footer:after { content: " "; display: table; }
#header:after, #content:after, #footnotes:after, #footer:after { clear: both; }

#header { margin-bottom: 2.5em; }
#header > h1 { color: #693c16; font-weight: normal; border-bottom: 1px solid #dcd2c9;}
#header span { color: #846b55; }
#header #revnumber { text-transform: capitalize; }
#header br { display: none; }
#header br + span { padding-left: 3px; }
#header br + span.author { padding-left: 0; }
#header br + span.author:before { content: ", "; }

#revdate {
	display: block;
	margin-top: 2.5em;
}

#toc { border-bottom: 1px solid #e6dfd8; padding-bottom: 1.25em; }
#toc > ul { margin-left: 0.25em; }
#toc ul.sectlevel0 > li > a { font-style: italic; }
#toc ul.sectlevel0 ul.sectlevel1 { margin-left: 0; margin-top: 0.5em; margin-bottom: 0.5em; }
#toc ul { list-style-type: none; }

#toctitle { color: #385dbd; }

@media only screen and (min-width: 768px) { body.toc2 { padding-left: 15em; padding-right: 0; }
  #toc.toc2 { position: fixed; width: 15em; left: 0; top: 0; border-right: 1px solid #e6dfd8; border-bottom: 0; z-index: 1000; padding: 1em; height: 100%; overflow: auto; }
  #toc.toc2 #toctitle { margin-top: 0; font-size: 1.2em; }
  #toc.toc2 > ul { font-size: .90em; }
  #toc.toc2 ul ul { margin-left: 0; padding-left: 1em; }
  #toc.toc2 ul.sectlevel0 ul.sectlevel1 { padding-left: 0; margin-top: 0.5em; margin-bottom: 0.5em; }
  body.toc2.toc-right { padding-left: 0; padding-right: 15em; }
  body.toc2.toc-right #toc.toc2 { border-right: 0; border-left: 1px solid #e6dfd8; left: auto; right: 0; } }
@media only screen and (min-width: 1280px) { body.toc2 { padding-left: 20em; padding-right: 0; }
  #toc.toc2 { width: 20em; }
  #toc.toc2 #toctitle { font-size: 1.375em; }
  #toc.toc2 > ul { font-size: 0.95em; }
  #toc.toc2 ul ul { padding-left: 1.25em; }
  body.toc2.toc-right { padding-left: 0; padding-right: 20em; } }
#content #toc { border-style: solid; border-width: 1px; border-color: #d9d9d9; margin-bottom: 1.25em; padding: 1.25em; background: #f2f2f2; border-width: 0; -webkit-border-radius: 6px; border-radius: 6px; }
#content #toc > :first-child { margin-top: 0; }
#content #toc > :last-child { margin-bottom: 0; }
#content #toc a { text-decoration: none; }

#content #toctitle { font-weight: bold; font-family: "Open Sans", Arial, sans-serif; font-size: 1em; padding-left: 0.125em; }

#footer { max-width: 100%; background-color: #23160c; padding: 1.25em; }

#footer-text { color: #deecf9; line-height: 1.44; }

.sect1 { padding-bottom: 1.25em; }

.sect1 + .sect1 { border-top: 1px solid #e6dfd8; }

#content h1 > a.anchor, h2 > a.anchor, h3 > a.anchor, #toctitle > a.anchor, .sidebarblock > .content > .title > a.anchor, h4 > a.anchor, h5 > a.anchor, h6 > a.anchor { position: absolute; width: 1em; margin-left: -1em; display: block; text-decoration: none; visibility: hidden; text-align: center; font-weight: normal; }
#content h1 > a.anchor:before, h2 > a.anchor:before, h3 > a.anchor:before, #toctitle > a.anchor:before, .sidebarblock > .content > .title > a.anchor:before, h4 > a.anchor:before, h5 > a.anchor:before, h6 > a.anchor:before { content: '\00A7'; font-size: .85em; vertical-align: text-top; display: block; margin-top: 0.05em; }
#content h1:hover > a.anchor, #content h1 > a.anchor:hover, h2:hover > a.anchor, h2 > a.anchor:hover, h3:hover > a.anchor, #toctitle:hover > a.anchor, .sidebarblock > .content > .title:hover > a.anchor, h3 > a.anchor:hover, #toctitle > a.anchor:hover, .sidebarblock > .content > .title > a.anchor:hover, h4:hover > a.anchor, h4 > a.anchor:hover, h5:hover > a.anchor, h5 > a.anchor:hover, h6:hover > a.anchor, h6 > a.anchor:hover { visibility: visible; }
#content h1 > a.link, h2 > a.link, h3 > a.link, #toctitle > a.link, .sidebarblock > .content > .title > a.link, h4 > a.link, h5 > a.link, h6 > a.link { color: #152347; text-decoration: none; }
#content h1 > a.link:hover, h2 > a.link:hover, h3 > a.link:hover, #toctitle > a.link:hover, .sidebarblock > .content > .title > a.link:hover, h4 > a.link:hover, h5 > a.link:hover, h6 > a.link:hover { color: #0f1933; }

.imageblock, .literalblock, .listingblock, .mathblock, .verseblock, .videoblock { margin-bottom: 1.25em; }

.admonitionblock td.content > .title, .exampleblock > .title, .imageblock > .title, .listingblock > .title, .literalblock > .title, .mathblock > .title, .openblock > .title, .paragraph > .title, .quoteblock > .title, .sidebarblock > .title, .tableblock > .title, .verseblock > .title, .videoblock > .title, .dlist > .title, .olist > .title, .ulist > .title, .qlist > .title, .hdlist > .title { text-align: left; font-weight: bold; }

.tableblock > caption { text-align: left; font-weight: bold; white-space: nowrap; overflow: visible; max-width: 0; }

table.tableblock #preamble > .sectionbody > .paragraph:first-of-type p { font-size: inherit; }

.admonitionblock > table { border: 0; background: none; width: 100%; }
.admonitionblock > table td.icon { text-align: center; width: 80px; }
.admonitionblock > table td.icon img { max-width: none; }
.admonitionblock > table td.icon .title { font-weight: bold; text-transform: uppercase; }
.admonitionblock > table td.content { padding-left: 1.125em; padding-right: 1.25em; border-left: 1px solid #dcd2c9; color: #846b55; }
.admonitionblock > table td.content > :last-child > :last-child { margin-bottom: 0; }

.exampleblock > .content { border-style: solid; border-width: 1px; border-color: #f3e0ce; margin-bottom: 1.25em; padding: 1.25em; background: #fdfaf7; -webkit-border-radius: 6px; border-radius: 6px; }
.exampleblock > .content > :first-child { margin-top: 0; }
.exampleblock > .content > :last-child { margin-bottom: 0; }
.exampleblock > .content h1, .exampleblock > .content h2, .exampleblock > .content h3, .exampleblock > .content #toctitle, .sidebarblock.exampleblock > .content > .title, .exampleblock > .content h4, .exampleblock > .content h5, .exampleblock > .content h6, .exampleblock > .content p { color: #333333; }
.exampleblock > .content h1, .exampleblock > .content h2, .exampleblock > .content h3, .exampleblock > .content #toctitle, .sidebarblock.exampleblock > .content > .title, .exampleblock > .content h4, .exampleblock > .content h5, .exampleblock > .content h6 { line-height: 1; margin-bottom: 0.625em; }
.exampleblock > .content h1.subheader, .exampleblock > .content h2.subheader, .exampleblock > .content h3.subheader, .exampleblock > .content .subheader#toctitle, .sidebarblock.exampleblock > .content > .subheader.title, .exampleblock > .content h4.subheader, .exampleblock > .content h5.subheader, .exampleblock > .content h6.subheader { line-height: 1.4; }

.exampleblock.result > .content { -webkit-box-shadow: 0 1px 8px #d9d9d9; box-shadow: 0 1px 8px #d9d9d9; }

.sidebarblock { border-style: solid; border-width: 1px; border-color: #d9d9d9; margin-bottom: 1.25em; padding: 1.25em; background: #f2f2f2; -webkit-border-radius: 6px; border-radius: 6px; }
.sidebarblock > :first-child { margin-top: 0; }
.sidebarblock > :last-child { margin-bottom: 0; }
.sidebarblock h1, .sidebarblock h2, .sidebarblock h3, .sidebarblock #toctitle, .sidebarblock > .content > .title, .sidebarblock h4, .sidebarblock h5, .sidebarblock h6, .sidebarblock p { color: #333333; }
.sidebarblock h1, .sidebarblock h2, .sidebarblock h3, .sidebarblock #toctitle, .sidebarblock > .content > .title, .sidebarblock h4, .sidebarblock h5, .sidebarblock h6 { line-height: 1; margin-bottom: 0.625em; }
.sidebarblock h1.subheader, .sidebarblock h2.subheader, .sidebarblock h3.subheader, .sidebarblock .subheader#toctitle, .sidebarblock > .content > .subheader.title, .sidebarblock h4.subheader, .sidebarblock h5.subheader, .sidebarblock h6.subheader { line-height: 1.4; }
.sidebarblock > .content > .title { color: #385dbd; margin-top: 0; line-height: 1.6; }

.exampleblock > .content > :last-child > :last-child, .exampleblock > .content .olist > ol > li:last-child > :last-child, .exampleblock > .content .ulist > ul > li:last-child > :last-child, .exampleblock > .content .qlist > ol > li:last-child > :last-child, .sidebarblock > .content > :last-child > :last-child, .sidebarblock > .content .olist > ol > li:last-child > :last-child, .sidebarblock > .content .ulist > ul > li:last-child > :last-child, .sidebarblock > .content .qlist > ol > li:last-child > :last-child { margin-bottom: 0; }

.literalblock pre:not([class]), .listingblock pre:not([class]) { background: url('../images/golo/pre-bg.png?1370460826'); }
.literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { border-width: 1px; border-style: solid; border-color: rgba(21, 35, 71, 0.1); -webkit-border-radius: 6px; border-radius: 6px; padding: 0.8em; word-wrap: break-word; }
.literalblock pre.nowrap, .literalblock pre[class].nowrap, .listingblock pre.nowrap, .listingblock pre[class].nowrap { overflow-x: auto; white-space: pre; word-wrap: normal; }
.literalblock pre > code, .literalblock pre[class] > code, .listingblock pre > code, .listingblock pre[class] > code { display: block; }
@media only screen { .literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { font-size: 0.72em; } }
@media only screen and (min-width: 768px) { .literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { font-size: 0.81em; } }
@media only screen and (min-width: 1280px) { .literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { font-size: 0.9em; } }

.listingblock pre.highlight { padding: 0; }
.listingblock pre.highlight > code { padding: 0.8em; }

.listingblock > .content { position: relative; }

.listingblock:hover code[class*=" language-"]:before { text-transform: uppercase; font-size: 0.9em; color: #999; position: absolute; top: 0.375em; right: 0.375em; }

.listingblock:hover code.asciidoc:before { content: "asciidoc"; }
.listingblock:hover code.clojure:before { content: "clojure"; }
.listingblock:hover code.css:before { content: "css"; }
.listingblock:hover code.groovy:before { content: "groovy"; }
.listingblock:hover code.html:before { content: "html"; }
.listingblock:hover code.java:before { content: "java"; }
.listingblock:hover code.javascript:before { content: "javascript"; }
.listingblock:hover code.python:before { content: "python"; }
.listingblock:hover code.ruby:before { content: "ruby"; }
.listingblock:hover code.sass:before { content: "sass"; }
.listingblock:hover code.scss:before { content: "scss"; }
.listingblock:hover code.xml:before { content: "xml"; }
.listingblock:hover code.yaml:before { content: "yaml"; }

.listingblock.terminal pre .command:before { content: attr(data-prompt); padding-right: 0.5em; color: #999; }

.listingblock.terminal pre .command:not([data-prompt]):before { content: '$'; }

table.pyhltable { border: 0; margin-bottom: 0; }

table.pyhltable td { vertical-align: top; padding-top: 0; padding-bottom: 0; }

table.pyhltable td.code { padding-left: .75em; padding-right: 0; }

.highlight.pygments .lineno, table.pyhltable td:not(.code) { color: #999; padding-left: 0; padding-right: .5em; border-right: 1px solid #dcd2c9; }

.highlight.pygments .lineno { display: inline-block; margin-right: .25em; }

table.pyhltable .linenodiv { background-color: transparent !important; padding-right: 0 !important; }

.quoteblock { margin: 0 0 1.25em; padding: 0.5625em 1.25em 0 1.1875em; border-left: 1px solid #dddddd; }
.quoteblock blockquote { margin: 0 0 1.25em 0; padding: 0 0 0.5625em 0; border: 0; }
.quoteblock blockquote > .paragraph:last-child p { margin-bottom: 0; }
.quoteblock .attribution { margin-top: -.25em; padding-bottom: 0.5625em; font-size: 0.8125em; color: #655241; }
.quoteblock .attribution br { display: none; }
.quoteblock .attribution cite { display: block; margin-bottom: 0.625em; }

table thead th, table tfoot th { font-weight: bold; }

table.tableblock.grid-all { border-collapse: separate; border-spacing: 1px; -webkit-border-radius: 6px; border-radius: 6px; border-top: 1px solid #e4e7ef; border-bottom: 1px solid #e4e7ef; }

table.tableblock.frame-topbot, table.tableblock.frame-none { border-left: 0; border-right: 0; }

table.tableblock.frame-sides, table.tableblock.frame-none { border-top: 0; border-bottom: 0; }

table.tableblock td .paragraph:last-child p > p:last-child, table.tableblock th > p:last-child, table.tableblock td > p:last-child { margin-bottom: 0; }

th.tableblock.halign-left, td.tableblock.halign-left { text-align: left; }

th.tableblock.halign-right, td.tableblock.halign-right { text-align: right; }

th.tableblock.halign-center, td.tableblock.halign-center { text-align: center; }

th.tableblock.valign-top, td.tableblock.valign-top { vertical-align: top; }

th.tableblock.valign-bottom, td.tableblock.valign-bottom { vertical-align: bottom; }

th.tableblock.valign-middle, td.tableblock.valign-middle { vertical-align: middle; }

tbody tr th { display: table-cell; line-height: 1.6; background: rgba(105, 60, 22, 0.25); }

tbody tr th, tbody tr th p, tfoot tr th, tfoot tr th p { color: #211306; font-weight: bold; }

td > div.verse { white-space: pre; }

ol { margin-left: 1.75em; }

ul li ol { margin-left: 1.5em; }

dl dd { margin-left: 1.125em; }

dl dd:last-child, dl dd:last-child > :last-child { margin-bottom: 0; }

ol > li p, ul > li p, ul dd, ol dd, .olist .olist, .ulist .ulist, .ulist .olist, .olist .ulist { margin-bottom: 0.625em; }

ul.unstyled, ol.unnumbered, ul.checklist, ul.none { list-style-type: none; }

ul.unstyled, ol.unnumbered, ul.checklist { margin-left: 0.625em; }

ul.checklist li > p:first-child > i[class^="icon-check"]:first-child, ul.checklist li > p:first-child > input[type="checkbox"]:first-child { margin-right: 0.25em; }

ul.checklist li > p:first-child > input[type="checkbox"]:first-child { position: relative; top: 1px; }

ul.inline { margin: 0 auto 0.625em auto; margin-left: -1.375em; margin-right: 0; padding: 0; list-style: none; overflow: hidden; }
ul.inline > li { list-style: none; float: left; margin-left: 1.375em; display: block; }
ul.inline > li > * { display: block; }

.unstyled dl dt { font-weight: normal; font-style: normal; }

ol.arabic { list-style-type: decimal; }

ol.decimal { list-style-type: decimal-leading-zero; }

ol.loweralpha { list-style-type: lower-alpha; }

ol.upperalpha { list-style-type: upper-alpha; }

ol.lowerroman { list-style-type: lower-roman; }

ol.upperroman { list-style-type: upper-roman; }

ol.lowergreek { list-style-type: lower-greek; }

.hdlist > table, .colist > table { border: 0; background: none; }
.hdlist > table > tbody > tr, .colist > table > tbody > tr { background: none; }

td.hdlist1 { padding-right: .75em; font-weight: bold; }

td.hdlist1, td.hdlist2 { vertical-align: top; }

.literalblock + .colist, .listingblock + .colist { margin-top: -0.5em; }

.colist > table tr > td:first-of-type { padding: 0 .75em; line-height: 1; }
.colist > table tr > td:last-of-type { padding: 0.25em 0; }

.qanda > ol > li > p > em:only-child { color: #063f40; }

.thumb, .th { line-height: 0; display: inline-block; border: solid 4px white; -webkit-box-shadow: 0 0 0 1px #dddddd; box-shadow: 0 0 0 1px #dddddd; }

.imageblock.left, .imageblock[style*="float: left"] { margin: 0.25em 0.625em 1.25em 0; }
.imageblock.right, .imageblock[style*="float: right"] { margin: 0.25em 0 1.25em 0.625em; }
.imageblock > .title { margin-bottom: 0; }
.imageblock.thumb, .imageblock.th { border-width: 6px; }
.imageblock.thumb > .title, .imageblock.th > .title { padding: 0 0.125em; }

.image.left, .image.right { margin-top: 0.25em; margin-bottom: 0.25em; display: inline-block; line-height: 0; }
.image.left { margin-right: 0.625em; }
.image.right { margin-left: 0.625em; }

a.image { text-decoration: none; }

span.footnote, span.footnoteref { vertical-align: super; font-size: 0.875em; }
span.footnote a, span.footnoteref a { text-decoration: none; }

#footnotes { padding-top: 0.75em; padding-bottom: 0.75em; margin-bottom: 0.625em; }
#footnotes hr { width: 20%; min-width: 6.25em; margin: -.25em 0 .75em 0; border-width: 1px 0 0 0; }
#footnotes .footnote { padding: 0 0.375em; line-height: 1.3; font-size: 0.875em; margin-left: 1.2em; text-indent: -1.2em; margin-bottom: .2em; }
#footnotes .footnote a:first-of-type { font-weight: bold; text-decoration: none; }
#footnotes .footnote:last-of-type { margin-bottom: 0; }

#content #footnotes { margin-top: -0.625em; margin-bottom: 0; padding: 0.75em 0; }

.gist .file-data > table { border: none; background: #fff; width: 100%; margin-bottom: 0; }
.gist .file-data > table td.line-data { width: 99%; }

div.unbreakable { page-break-inside: avoid; }

.big { font-size: larger; }

.small { font-size: smaller; }

.underline { text-decoration: underline; }

.overline { text-decoration: overline; }

.line-through { text-decoration: line-through; }

.aqua { color: #00bfbf; }

.aqua-background { background-color: #00fafa; }

.black { color: black; }

.black-background { background-color: black; }

.blue { color: #0000bf; }

.blue-background { background-color: #0000fa; }

.fuchsia { color: #bf00bf; }

.fuchsia-background { background-color: #fa00fa; }

.gray { color: #606060; }

.gray-background { background-color: #7d7d7d; }

.green { color: #006000; }

.green-background { background-color: #007d00; }

.lime { color: #00bf00; }

.lime-background { background-color: #00fa00; }

.maroon { color: #600000; }

.maroon-background { background-color: #7d0000; }

.navy { color: #000060; }

.navy-background { background-color: #00007d; }

.olive { color: #606000; }

.olive-background { background-color: #7d7d00; }

.purple { color: #600060; }

.purple-background { background-color: #7d007d; }

.red { color: #bf0000; }

.red-background { background-color: #fa0000; }

.silver { color: #909090; }

.silver-background { background-color: #bcbcbc; }

.teal { color: #006060; }

.teal-background { background-color: #007d7d; }

.white { color: #bfbfbf; }

.white-background { background-color: #fafafa; }

.yellow { color: #bfbf00; }

.yellow-background { background-color: #fafa00; }

span.icon > [class^="icon-"], span.icon > [class*=" icon-"] { cursor: default; }

.admonitionblock td.icon [class^="icon-"]:before { font-size: 2.5em; text-shadow: 1px 1px 2px rgba(0, 0, 0, 0.5); cursor: default; }
.admonitionblock td.icon .icon-note:before { content: "\f05a"; color: #095557; color: #064042; }
.admonitionblock td.icon .icon-tip:before { content: "\f0eb"; text-shadow: 1px 1px 2px rgba(155, 155, 0, 0.8); color: #111; }
.admonitionblock td.icon .icon-warning:before { content: "\f071"; color: #bf6900; }
.admonitionblock td.icon .icon-caution:before { content: "\f06d"; color: #bf3400; }
.admonitionblock td.icon .icon-important:before { content: "\f06a"; color: #bf0000; }

.conum { display: inline-block; color: white !important; background-color: #211306; -webkit-border-radius: 100px; border-radius: 100px; text-align: center; width: 20px; height: 20px; font-size: 12px; font-weight: bold; line-height: 20px; font-family: Arial, sans-serif; font-style: normal; position: relative; top: -2px; letter-spacing: -1px; }
.conum * { color: white !important; }
.conum + b { display: none; }
.conum:after { content: attr(data-value); }
.conum:not([data-value]):empty { display: none; }

body { background: url('../images/golo/body-bg.png?1370460826') #fdfaf7 repeat; }

#toc.toc2 ul ul { padding-left: 1.75em; }

#toctitle { color: #152347; }

#header h1 { font-weight: bold; position: relative; left: -0.0625em; }
#header h1 span.lo { color: #dc9424; }

#content h2, #content h3, #content #toctitle, #content .sidebarblock > .content > .title, #content h4, #content h5, #content #toctitle { font-weight: normal; position: relative; left: -0.0625em; }
#content h2 { font-weight: bold; }

.literalblock .content pre.highlight, .listingblock .content pre.highlight { background: url('../images/golo/pre-bg.png?1370460826'); }

.admonitionblock > table td.content { border-color: #e6dfd8; }

table.tableblock.grid-all { -webkit-border-radius: 0; border-radius: 0; }

#footer { background-color: #23160c; }

.imageblock .title { text-align: center; }

#content h1.sect0 {
  font-size: 48px;
}

#toc>ul>li>a {
  font-size: large;
}

</style>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.2.0/css/font-awesome.min.css">
<style>
/* Stylesheet for CodeRay to match GitHub theme | MIT License | https://foundation.zurb.com */
/*pre.CodeRay {background-color:#f7f7f8;}*/
.CodeRay .line-numbers{border-right:1px solid #d8d8d8;padding:0 0.5em 0 .25em}
.CodeRay span.line-numbers{display:inline-block;margin-right:.5em;color:rgba(0,0,0,.3)}
.CodeRay .line-numbers strong{font-weight: normal}
table.CodeRay{border-collapse:separate;border-spacing:0;margin-bottom:0;border:0;background:none}
table.CodeRay td{vertical-align: top}
table.CodeRay td.line-numbers{text-align:right}
table.CodeRay td.line-numbers>pre{padding:0;color:rgba(0,0,0,.3)}
table.CodeRay td.code{padding:0 0 0 .5em}
table.CodeRay td.code>pre{padding:0}
.CodeRay .debug{color:#fff !important;background:#000080 !important}
.CodeRay .annotation{color:#007}
.CodeRay .attribute-name{color:#000080}
.CodeRay .attribute-value{color:#700}
.CodeRay .binary{color:#509}
.CodeRay .comment{color:#998;font-style:italic}
.CodeRay .char{color:#04d}
.CodeRay .char .content{color:#04d}
.CodeRay .char .delimiter{color:#039}
.CodeRay .class{color:#458;font-weight:bold}
.CodeRay .complex{color:#a08}
.CodeRay .constant,.CodeRay .predefined-constant{color:#008080}
.CodeRay .color{color:#099}
.CodeRay .class-variable{color:#369}
.CodeRay .decorator{color:#b0b}
.CodeRay .definition{color:#099}
.CodeRay .delimiter{color:#000}
.CodeRay .doc{color:#970}
.CodeRay .doctype{color:#34b}
.CodeRay .doc-string{color:#d42}
.CodeRay .escape{color:#666}
.CodeRay .entity{color:#800}
.CodeRay .error{color:#808}
.CodeRay .exception{color:inherit}
.CodeRay .filename{color:#099}
.CodeRay .function{color:#900;font-weight:bold}
.CodeRay .global-variable{color:#008080}
.CodeRay .hex{color:#058}
.CodeRay .integer,.CodeRay .float{color:#099}
.CodeRay .include{color:#555}
.CodeRay .inline{color:#00}
.CodeRay .inline .inline{background:#ccc}
.CodeRay .inline .inline .inline{background:#bbb}
.CodeRay .inline .inline-delimiter{color:#d14}
.CodeRay .inline-delimiter{color:#d14}
.CodeRay .important{color:#555;font-weight:bold}
.CodeRay .interpreted{color:#b2b}
.CodeRay .instance-variable{color:#008080}
.CodeRay .label{color:#970}
.CodeRay .local-variable{color:#963}
.CodeRay .octal{color:#40e}
.CodeRay .predefined{color:#369}
.CodeRay .preprocessor{color:#579}
.CodeRay .pseudo-class{color:#555}
.CodeRay .directive{font-weight:bold}
.CodeRay .type{font-weight:bold}
.CodeRay .predefined-type{color:inherit}
.CodeRay .reserved,.CodeRay .keyword {color:#000;font-weight:bold}
.CodeRay .key{color:#808}
.CodeRay .key .delimiter{color:#606}
.CodeRay .key .char{color:#80f}
.CodeRay .value{color:#088}
.CodeRay .regexp .delimiter{color:#808}
.CodeRay .regexp .content{color:#808}
.CodeRay .regexp .modifier{color:#808}
.CodeRay .regexp .char{color:#d14}
.CodeRay .regexp .function{color:#404;font-weight:bold}
.CodeRay .string{color:#d20}
.CodeRay .string .string .string{background:#ffd0d0}
.CodeRay .string .content{color:#d14}
.CodeRay .string .char{color:#d14}
.CodeRay .string .delimiter{color:#d14}
.CodeRay .shell{color:#d14}
.CodeRay .shell .delimiter{color:#d14}
.CodeRay .symbol{color:#990073}
.CodeRay .symbol .content{color:#a60}
.CodeRay .symbol .delimiter{color:#630}
.CodeRay .tag{color:#008080}
.CodeRay .tag-special{color:#d70}
.CodeRay .variable{color:#036}
.CodeRay .insert{background:#afa}
.CodeRay .delete{background:#faa}
.CodeRay .change{color:#aaf;background:#007}
.CodeRay .head{color:#f8f;background:#505}
.CodeRay .insert .insert{color:#080}
.CodeRay .delete .delete{color:#800}
.CodeRay .change .change{color:#66f}
.CodeRay .head .head{color:#f4f}
</style>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/semantic-ui/1.6.2/semantic.min.css"/>
<link rel="stylesheet" href="https://projectreactor.io/stylesheets/docs.css"/>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.0.3/jquery.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/semantic-ui/1.6.2/semantic.min.js"></script>
<script>$(function(){
	var el = document.createElement("script");
	el.setAttribute("src", "https://projectreactor.io/javascripts/docs.js");
	document.body.appendChild(el);
	$('.ui.dropdown').dropdown();
})</script>
<style>
	body #toc.toc2 {
		padding-top: 42px;
		z-index:100;
	}
</style>
</head>
<body class="book toc2 toc-left">
<div id="header">
<h1>Reactor Guide</h1>
<div class="details">
<span id="author" class="author">Stephane Maldini</span><br>
<span id="author2" class="author">Jon Brisbin</span><br>
<span id="revdate">2.0.8.BUILD-SNAPSHOT</span>
</div>
<div id="toc" class="toc2">
<div id="toctitle">Table of Contents</div>
<ul class="sectlevel1">
<li><a href="#getting-started"><strong>Introducing Reactor</strong></a>
<ul class="sectlevel2">
<li><a href="#start">What is Reactor ?</a></li>
<li><a href="#_about_the_project">About the Project</a></li>
<li><a href="#_requirements">Requirements</a></li>
<li><a href="#architecture">Architecture Overview</a></li>
<li><a href="#reactivestreams">Reactive Streams</a></li>
<li><a href="#rx">Reactive Extensions</a></li>
</ul>
</li>
<li><a href="#reactor-core"><strong>reactor-core</strong></a>
<ul class="sectlevel1">
<li><a href="#_core_overview">Core Overview</a></li>
<li><a href="#core-functional">Functional Artefacts</a>
<ul class="sectlevel2">
<li><a href="#_organizing_functional_blocks">Organizing Functional Blocks</a></li>
<li><a href="#_tuples">Tuples</a></li>
</ul>
</li>
<li><a href="#core-dispatchers">Environment and Dispatchers</a>
<ul class="sectlevel2">
<li><a href="#_environment">Environment</a></li>
<li><a href="#_dispatchers">Dispatchers</a></li>
<li><a href="#_dispatchersupplier">DispatcherSupplier</a></li>
<li><a href="#_timers">Timers</a></li>
</ul>
</li>
<li><a href="#core-processor">Core Processors</a></li>
<li><a href="#_ringbuffer_processors">RingBuffer Processors</a>
<ul class="sectlevel2">
<li><a href="#core-rbp">RingBufferProcessor</a></li>
<li><a href="#work">RingBufferWorkProcessor</a></li>
</ul>
</li>
<li><a href="#core-codecs">Codecs and Buffer</a></li>
</ul>
</li>
<li><a href="#reactor-stream"><strong>reactor-stream</strong></a>
<ul class="sectlevel1">
<li><a href="#streams">Coordinating tasks with Streams and Promises</a></li>
<li><a href="#streams-basics">Streams Basics</a></li>
<li><a href="#_creating_streams_and_promises">Creating Streams and Promises</a>
<ul class="sectlevel2">
<li><a href="#_from_cold_data_sources">From Cold Data Sources</a></li>
<li><a href="#streams-reactivestreams">From Existing Reactive Publishers</a></li>
<li><a href="#_from_custom_reactive_publishers">From Custom Reactive Publishers</a></li>
<li><a href="#_from_hot_data_sources">From Hot Data Sources</a></li>
<li><a href="#wireup">Wiring up a Stream</a></li>
<li><a href="#stream-capacity">Setting Capacity</a></li>
<li><a href="#_functional_composition">Functional Composition</a></li>
</ul>
</li>
<li><a href="#streams-multithreading">Understanding the threading model</a></li>
<li><a href="#streams-microbatching">MicroBatching</a>
<ul class="sectlevel2">
<li><a href="#_into_buffers">Into Buffers</a></li>
<li><a href="#_into_windows">Into Windows</a></li>
</ul>
</li>
<li><a href="#streams-backpressure">Backpressure and Overflow</a></li>
<li><a href="#streams-combine">Combinatory Operations</a></li>
<li><a href="#streams-microservice">MicroServices</a>
<ul class="sectlevel2">
<li><a href="#streams-microservice-start">Creating Non-Blocking Services</a></li>
<li><a href="#streams-microservice-compose">Composing multiple Services Calls</a></li>
<li><a href="#streams-microservice-backpressure">Supporting Reactive Backpressure</a></li>
</ul>
</li>
<li><a href="#streams-errors">Error Handling</a></li>
<li><a href="#streams-persistent">Persisting Stream Data</a></li>
<li><a href="#streams-analytics">Analytics</a></li>
<li><a href="#streams-partition">Partitioning</a></li>
<li><a href="#streams-notrx">Other API beyond Rx</a></li>
</ul>
</li>
<li><a href="#reactor-bus"><strong>reactor-bus</strong></a>
<ul class="sectlevel1">
<li><a href="#bus">Routing data</a></li>
<li><a href="#bus-publish-subscribe">Publish/Subscribe</a></li>
<li><a href="#bus-request-reply">Request/Reply</a>
<ul class="sectlevel2">
<li><a href="#_cancelling_a_task">Cancelling a Task</a></li>
</ul>
</li>
<li><a href="#bus-registry">Registry</a></li>
</ul>
</li>
<li><a href="#reactor-net"><strong>reactor-net</strong></a>
<ul class="sectlevel1">
<li><a href="#_asynchronous_tcp_udp_and_http">Asynchronous TCP, UDP and HTTP</a>
<ul class="sectlevel2">
<li><a href="#net-overview">Overview</a></li>
<li><a href="#_channels">Channels</a></li>
<li><a href="#_channel_handlers">Channel Handlers</a></li>
<li><a href="#_specifications">Specifications</a></li>
<li><a href="#_client_specification">Client Specification</a></li>
<li><a href="#_server_specification">Server Specification</a></li>
<li><a href="#net-backpressure">Backpressure</a></li>
</ul>
</li>
<li><a href="#net-tcp101">TCP 101</a>
<ul class="sectlevel2">
<li><a href="#_start_and_stop">Start and Stop</a></li>
<li><a href="#_writing_data">Writing Data</a></li>
<li><a href="#_flushing_strategies">Flushing Strategies</a></li>
<li><a href="#_consuming_data">Consuming Data</a></li>
<li><a href="#_backpressure_strategies">Backpressure Strategies</a></li>
<li><a href="#_closing_the_channel">Closing the Channel</a></li>
</ul>
</li>
<li><a href="#net-http101">HTTP 101</a>
<ul class="sectlevel2">
<li><a href="#_start_and_stop_2">Start and Stop</a></li>
<li><a href="#_routing_http">Routing HTTP</a></li>
<li><a href="#_routing_websocket">Routing WebSocket</a></li>
<li><a href="#_writing_data_2">Writing Data</a></li>
<li><a href="#_flushing_strategies_2">Flushing Strategies</a></li>
<li><a href="#_consuming_data_2">Consuming Data</a></li>
<li><a href="#_backpressure_strategies_2">Backpressure Strategies</a></li>
<li><a href="#_closing_the_channel_2">Closing the Channel</a></li>
</ul>
</li>
<li><a href="#net-endToEnd">End To End</a></li>
</ul>
</li>
<li><a href="#reactor-extensions"><strong>Extensions</strong></a>
<ul class="sectlevel1">
<li><a href="#reactor-spring">Spring Support</a>
<ul class="sectlevel2">
<li><a href="#_spring_ecosystem_support">Spring Ecosystem Support</a></li>
<li><a href="#spring-basics">Spring Core Basics</a></li>
<li><a href="#spring-boot">Reactor with Spring Boot</a></li>
<li><a href="#spring-integration">Reactor with Spring Messaging</a></li>
<li><a href="#spring-integration-messaging">Reactor with Spring Integration</a></li>
<li><a href="#_spring_integration_java_dsl">Spring Integration Java DSL</a></li>
</ul>
</li>
<li><a href="#spring-xd">Reactor with Spring XD</a></li>
<li><a href="#_groovy_extensions">Groovy extensions</a>
<ul class="sectlevel2">
<li><a href="#_groovy_support">Groovy support</a></li>
<li><a href="#_grails_support">Grails support</a></li>
</ul>
</li>
<li><a href="#clojure">Clojure support</a></li>
<li><a href="#reactor-samples">Cookbook</a>
<ul class="sectlevel2">
<li><a href="#recipe-filestream">Building a simple File Stream</a></li>
<li><a href="#recipes-circuitbreaker">Building a Quick Circuit Breaker</a></li>
<li><a href="#_building_efficient_data_pipelines">Building Efficient Data Pipelines</a></li>
<li><a href="#_building_non_blocking_microservices">Building Non-Blocking MicroServices</a></li>
<li><a href="#_building_cqrs_like_applications">Building CQRS-like Applications</a></li>
<li><a href="#_other_example_applications">Other Example Applications</a></li>
</ul>
</li>
</ul>
</li>
</ul>
</div>
</div>
<div id="content">
<div id="preamble">
<div class="sectionbody">
<nav class="ui fixed inverted menu">
	<div class="header item">
		<a href="/">Project Reactor</a>
	</div>
	<div class="right menu">
		<div class="ui pointing dropdown link item" title="Reference">
			<i class="book icon"></i>
			<div class="menu">
				<a class="active item" title="HTML" href="https://projectreactor.io/docs/reference/">HTML</a>
				<a class="item" title="EPUB" href="https://drone.io/github.com/reactor/reactor/files/build/reference/epub/reactor-reference.epub">EPUB</a>
				<a class="item" title="PDF" href="https://drone.io/github.com/reactor/reactor/files/build/reference/pdf/reactor-reference.pdf">PDF</a>
			</div>
		</div>
		<a class="item" href="https://github.com/reactor/reactor/" title="Source Code">
			<i class="github icon"></i>
		</a>
		<a class="item" href="https://github.com/reactor/reactor/issues" title="Bug Tracker">
			<i class="bug icon"></i>
		</a>
		<a class="item" href="https://stackoverflow.com/search?q=%23reactor" title="Community Discussion">
			<i class="comments icon"></i>
		</a>
	</div>
</nav>
</div>
</div>
<div class="sect1">
<h2 id="getting-started"><strong>Introducing Reactor</strong></h2>
<div class="sectionbody">
<div class="quoteblock">
<blockquote>
Reactor is a foundational library for building demanding, realtime <strong>Data-Streaming</strong> applications and micro, nano, or pico-services that must exhibit <strong>Low-Latency</strong> and be <strong>Fault-Tolerant</strong>.
</blockquote>
<div class="attribution">
&#8212; Preface<br>
<cite>TL;DR</cite>
</div>
</div>
<div class="sect2">
<h3 id="start">What is Reactor ?</h3>
<div class="paragraph">
<p>So you came to have a look at Reactor. Maybe you typed some keywords into your favorite search engine like <em>Reactive</em>,
<em>Spring+Reactive</em>, <em>Asynchronous+Java</em> or just <em>What the heck is Reactor?</em>. In a nutshell Reactor is a lightweight, foundational library for the JVM that helps your service or application to <em>efficiently</em> and <em>asynchronously</em> pass messages.</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">What do you mean by "efficiently"?</div>
<div class="ulist">
<ul>
<li>
<p>Little to no <strong>memory</strong> garbage created just to pass a message from A to B.</p>
</li>
<li>
<p>Handle <strong>overflow</strong> when consumers are slower at processing messages than the producer is at producing them.</p>
</li>
<li>
<p>Provide for <strong>asynchronous flow</strong>--without blocking&#8212;&#8203;if at all possible.</p>
</li>
</ul>
</div>
</div>
</div>
<div class="paragraph">
<p>From empirical studies (mostly <em>#rage</em> and <em>#drunk</em> tweets), we know that asynchronous programming is hard&#8212;&#8203;especially when a platform like the JVM offers so many options. Reactor aims to be truly non-blocking for a majority of use cases and we offer an API that is measurably more efficient than relying on low-level primitives from the JDK&#8217;s <em>java.util.concurrent</em> library. Reactor provides alternatives to (and discourages the use of):</p>
</div>
<div class="ulist">
<ul>
<li>
<p>Blocking wait : e.g. Future.<em>get()</em></p>
</li>
<li>
<p>Unsafe data access : e.g. ReentrantLock.<em>lock()</em></p>
</li>
<li>
<p>Exception Bubbles : e.g. try&#8230;&#8203;catch&#8230;&#8203;finally</p>
</li>
<li>
<p>Synchronization blocks : e.g. synchronized{ }</p>
</li>
<li>
<p>Wrapper Allocation (GC Pressure) : e.g. new Wrapper&lt;T&gt;(event)</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>Being non-blocking matters&#8212;&#8203;especially when scaling message-passing becomes critical (10k msg/s, 100k msg/s 1M&#8230;&#8203;). There is some theory behind this (see <a href="https://en.wikipedia.org/wiki/Amdahl%27s_law">Amdahl&#8217;s Law</a>), but we get bored and distracted easily, so let&#8217;s first appeal to common sense.</p>
</div>
<div class="paragraph">
<p>Let&#8217;s say you use a pure <a href="https://docs.oracle.com/javase/tutorial/essential/concurrency/executors.html">Executor</a> approach:</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="directive">private</span> <span class="predefined-type">ExecutorService</span>  threadPool = <span class="predefined-type">Executors</span>.newFixedThreadPool(<span class="integer">8</span>);

<span class="directive">final</span> <span class="predefined-type">List</span>&lt;T&gt; batches = <span class="keyword">new</span> <span class="predefined-type">ArrayList</span>&lt;T&gt;();

<span class="predefined-type">Callable</span>&lt;T&gt; t = <span class="keyword">new</span> <span class="predefined-type">Callable</span>&lt;T&gt;() { <i class="conum" data-value="1"></i><b>(1)</b>

    <span class="directive">public</span> T run() {
        <span class="directive">synchronized</span>(batches) { <i class="conum" data-value="2"></i><b>(2)</b>
            T result = callDatabase(msg); <i class="conum" data-value="3"></i><b>(3)</b>
            batches.add(result);
            <span class="keyword">return</span> result;
        }
    }
};

<span class="predefined-type">Future</span>&lt;T&gt; f = threadPool.submit(t); <i class="conum" data-value="4"></i><b>(4)</b>
T result = f.get() <i class="conum" data-value="5"></i><b>(5)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Allocate Callable&#8212;&#8203;might lead to GC pressure.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Synchronization will force stop-and-check for every thread.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Potentially consumes slower than producer produces.</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Use a ThreadPool to pass the task to the target thread&#8212;&#8203;definitely produces GC pressure via FutureTask.</td>
</tr>
<tr>
<td><i class="conum" data-value="5"></i><b>5</b></td>
<td>Block until callDatabase() replies.</td>
</tr>
</table>
</div>
<div class="paragraph">
<p>In this simple example, it&#8217;s easy to point out why scale-up is very limited:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>Allocating objects might cause <strong>GC pauses</strong>, especially if the tasks stick around too long.</p>
<div class="ulist">
<ul>
<li>
<p>Every GC Pause will degrade performance globally.</p>
</li>
</ul>
</div>
</li>
<li>
<p>A Queue is <strong>unbounded</strong> by default. Because of the database call, tasks will pile up.</p>
<div class="ulist">
<ul>
<li>
<p>A backlog is not really a Memory Leak but the side effects are just as nasty: more objects to scan during GC pauses; risk of losing important bits of data; etc&#8230;&#8203;</p>
</li>
<li>
<p>Classic Linked Queues generate memory pressure by allocating Nodes. Lots of them.</p>
</li>
</ul>
</div>
</li>
<li>
<p>A vicious cycle kicks-in when <strong>blocking replies</strong> are used.</p>
<div class="ulist">
<ul>
<li>
<p>Blocking replies will cause producer slow-down. In practice, the flow becomes basically <strong>synchronous</strong> since we have to wait for each reply before submitting more tasks.</p>
</li>
<li>
<p>Any Exception thrown during the conversation with the datastore will be passed in an uncontrolled fashion to the producer, negating any fault-tolerance normally available by segregating work around a Thread boundary.</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
<div class="paragraph">
<p>Being fully and truly non-blocking is hard to achieve&#8212;&#8203;especially in a world of distributed systems which have fashionable monikers like <strong>Micro-Service Architectures</strong>. Reactor, however, makes few compromises and tries to leverage the best patterns available so the developer doesn&#8217;t have to feel like they&#8217;re writing a mathematical thesis rather than an asynchronous nanoservice.</p>
</div>
<div class="paragraph">
<p>Nothing travels faster than light (besides gossip and viral cat videos) and latency is a real-world concern every system has to deal with at some point. To that end:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">Reactor offers a framework that helps you mitigate nasty latency-induced side-effects in your application and do it with minimal overhead by:</div>
<div class="ulist">
<ul>
<li>
<p>Leveraging some smart structures, we traded-off the <strong>allocation issue</strong> at runtime with pre-allocation at startup-time;</p>
</li>
<li>
<p>Main message-passing structures come <strong>bounded</strong> so we don&#8217;t pile up tasks infinitely;</p>
</li>
<li>
<p>Using popular patterns such as <strong>Reactive and Event-Driven Architectures</strong>, we offer <strong>non-blocking end-to-end flows</strong> including replies;</p>
</li>
<li>
<p>Implementing the new <a href="#reactivestreams">Reactive Streams</a> Standard, to make bounded structures <strong>efficient</strong> by not requesting more than their current capacity;</p>
</li>
<li>
<p>Applied these concepts to <a href="#net-overview">IPC</a> and provide <strong>non-blocking IO drivers</strong> that understand flow-control;</p>
</li>
<li>
<p>Expose a Functional API to help developers organize their code in a <strong>side-effect free</strong> way, which helps you determine where you are thread-safe and fault-tolerant.</p>
</li>
</ul>
</div>
</div>
</div>
</div>
<div class="sect2">
<h3 id="_about_the_project">About the Project</h3>
<div class="paragraph">
<p>The project started in 2012, with a long internal incubation time. Reactor 1.x appeared in 2013. Reactor 1 has been deployed successfully by various organizations, both Open Source (e.g. Meltdown) and Commercial (e.g. Pivotal RTI). In 2014 we started collaborating on the emerging <a href="gettingstarted..html#reactivestreams">Reactive Streams Standard</a> and started a massive re-engineering targeting April 2015 for version 2.0. The Reactive Streams Standard closed the last gap in our <em>Dispatching</em> mechanism: controlling how much in-flight data was hitting Thread boundaries.</p>
</div>
<div class="paragraph">
<p>Parallel to that work we also decided to re-align some of our Event-Driven and Task Coordination API to the increasingly popular and documented <a href="gettingstarted..html#rx">Reactive Extensions</a>.</p>
</div>
<div class="paragraph">
<p>Reactor is sponsored by <a href="https://pivotal.io">Pivotal</a> where the two core committers are employed. Since Pivotal is also the home of the Spring Framework and many of our colleagues are core committers to the various Spring efforts, we both provide integration support from Reactor to Spring as well as support some important functionality of the Spring Framework like the STOMP broker relay in <em>spring-messaging</em>. That said, we don&#8217;t force anyone to adopt Spring just to use Reactor. We remain an embeddable toolkit "for the Reactive masses". In fact one of the goals of Reactor is to stay un-opinionated in the ways you solve asynchronous and functional problems.</p>
</div>
<div class="paragraph">
<p>Reactor is <a href="https://www.apache.org/licenses/LICENSE-2.0.html">Apache 2.0 licensed</a> and available on <a href="https://github.com/reactor/reactor">GitHub</a>.</p>
</div>
</div>
<div class="sect2">
<h3 id="_requirements">Requirements</h3>
<div class="ulist">
<ul>
<li>
<p>Reactor needs at minimum Java 7 to execute.</p>
<div class="ulist">
<ul>
<li>
<p>But the full expressive potential of functional composition happens with Java 8 Lambdas.</p>
</li>
<li>
<p>As a fallback have a look at Spring, Clojure or Groovy extensions.</p>
</li>
</ul>
</div>
</li>
<li>
<p>Reactor runs at full capacity when the JVM supports <strong>Unsafe</strong> access (e.g., not the case for Android).</p>
<div class="ulist">
<ul>
<li>
<p>All <strong>RingBuffer</strong> based features will not work when Unsafe is missing.</p>
</li>
</ul>
</div>
</li>
<li>
<p>Reactor is packaged as traditional JAR archives in Maven Central and can be pulled into any JVM project as a dependency using your preferred build tool.</p>
</li>
</ul>
</div>
</div>
<div class="sect2">
<h3 id="architecture">Architecture Overview</h3>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/modules.png"><img src="images/modules.png" alt="Module Organization" width="500"></a>
</div>
<div class="title">Figure 1. The main modules present in Reactor 2.0</div>
</div>
<div class="paragraph">
<p>The Reactor codebase is divided into several submodules to help you pick the ones that suit your needs while not burdening you with functionality you don&#8217;t need.</p>
</div>
<div class="paragraph">
<p>Following are some examples of how one might mix-and-match reactive technologies and Reactor modules to achieve your asynchronous goals:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>Spring XD + Reactor-Net (Core/Stream) : Use Reactor as a Sink/Source IO driver.</p>
</li>
<li>
<p>Grails | Spring + Reactor-Stream (Core) : Use Stream and Promise for background Processing.</p>
</li>
<li>
<p>Spring Data + Reactor-Bus (Core) : Emit Database Events (Save/Delete/&#8230;&#8203;).</p>
</li>
<li>
<p>Spring Integration Java DSL + Reactor Stream (Core) : Microbatch MessageChannel from Spring Integration.</p>
</li>
<li>
<p>RxJavaReactiveStreams + RxJava + Reactor-Core : Combine rich composition with efficient asynchronous IO Processor</p>
</li>
<li>
<p>RxJavaReactiveStreams + RxJava + Reactor-Net (Core/Stream) : Compose input data with RxJava and gate with Async IO drivers.</p>
</li>
</ul>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/overview.png"><img src="images/overview.png" alt="Architecture Overview" width="650"></a>
</div>
<div class="title">Figure 2. A <strong>quick</strong> overview of how Reactor modules depend on one another</div>
</div>
</div>
<div class="sect2">
<h3 id="reactivestreams">Reactive Streams</h3>
<div class="paragraph">
<p><a href="https://www.reactive-streams.org">Reactive Streams</a> is a new standard, adopted by different vendors and tech industrials including Netflix, Oracle, Pivotal or Typesafe with a target to include the specification into Java 9 and onwards.</p>
</div>
<div class="paragraph">
<p>The aim of the standard is to provide (a)synchronous data sequences with a flow-control mechanism. The specification is fairly light and first targets the JVM.
It comes with 4 Java Interfaces, a TCK and a handful of examples. It is quite straightforward to implement the 4 interfaces for the need,
but the meat of the project is actually the behaviors verified by the TCK. A provider is qualified <em>Reactive Streams Ready</em> since
it successfully passed the TCK for the implementing classes, which fortunately we did.</p>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<img src="images/rs.png" alt="The Reactive Streams Contract" width="500">
</div>
<div class="title">Figure 3. The Reactive Streams Contract</div>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">The Reactive Streams Interfaces</div>
<div class="ulist">
<ul>
<li>
<p><a href="https://github.com/reactive-streams/reactive-streams-jvm/blob/master/api/src/main/java/org/reactivestreams/Publisher.java">org.reactivestreams.Pubslisher</a>: A source of data (from 0 to N signals where N can be unlimited). It optionally provides for 2 terminal events: error and completion.</p>
</li>
<li>
<p><a href="https://github.com/reactive-streams/reactive-streams-jvm/blob/master/api/src/main/java/org/reactivestreams/Subscriber.java">org.reactivestreams.Subscriber</a>: A consumer of a data sequence (from 0 to N signals where N can be unlimited). It receives a subscription on initialization to <em>request</em> how many data it wants to process next. The other callbacks interact with the data sequence signals: next (new message) and the optional completion/error.</p>
</li>
<li>
<p><a href="https://github.com/reactive-streams/reactive-streams-jvm/blob/master/api/src/main/java/org/reactivestreams/Subscription.java">org.reactivestreams.Subscription</a>: A small tracker passed on initialization to the Subscriber. It controls how many data we are ready to consume and when do we want to stop consuming (cancel).</p>
</li>
<li>
<p><a href="https://github.com/reactive-streams/reactive-streams-jvm/blob/master/api/src/main/java/org/reactivestreams/Processor.java">org.reactivestreams.Processor</a>: A marker for components that are both Subscriber and Publisher!</p>
</li>
</ul>
</div>
</div>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<img src="images/signals.png" alt="The Publishing Sequence" width="400">
</div>
<div class="title">Figure 4. The Reactive Streams publishing protocol</div>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">There are two ways to request data to a Publisher from a Subscriber, through the passed Subscription:</div>
<div class="ulist">
<ul>
<li>
<p><strong>Unbounded</strong>: On Subscribe, just call <em>Subscription#request(Long.MAX_VALUE)</em>.</p>
</li>
<li>
<p><strong>Bounded</strong>: On Subscribe, keep a reference to Subscription and hit its <em>request(long)</em> method when the Subscriber is ready to process data.</p>
<div class="ulist">
<ul>
<li>
<p>Typically, Subscribers will request an initial set of data, or even 1 data on Subscribe</p>
</li>
<li>
<p>Then after onNext has been deemed successful (e.g. after Commit, Flush etc&#8230;&#8203;), request more data</p>
</li>
<li>
<p>It is encouraged to use a linear number of requests. Try avoiding overlapping requests, e.g. requesting 10 more data every next signal.</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 1. What are the artifacts that Reactor directly use so far:</caption>
<colgroup>
<col style="width: 25%;">
<col style="width: 25%;">
<col style="width: 25%;">
<col style="width: 25%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top">Reactive Streams</th>
<th class="tableblock halign-left valign-top">Reactor Module(s)</th>
<th class="tableblock halign-left valign-top">Implementation(s)</th>
<th class="tableblock halign-left valign-top">Description</th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Processor</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor-core, reactor-stream</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.core.processor.*, reactor.rx.*</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">In Core, we offer backpressure-ready RingBuffer*Processor and more, in Stream we have a full set of Operations and Broadcasters.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Publisher</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor-core, reactor-bus, reactor-stream, reactor-net</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.core.processor.*, reactor.rx.stream.*, reactor.rx.action.*, reactor.io.net.*</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">In Core, processors implement Publisher. In Bus we publish an unbounded emission of routed events. In Stream, our Stream extensions directly implement Publisher. In Net, Channels implement Publisher to consume incoming data, we also provide publishers for flush and close callbacks.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Subscriber</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor-core, reactor-bus, reactor-stream, reactor-net</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.core.processor.*, reactor.bus.EventBus.*, reactor.rx.action.*, reactor.io.net.impl.*</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">In Core, our processor implement Subscriber. In Bus, we expose bus capacities with unbounded Publisher/Subscriber. In Stream, actions are Subscribers computing specific callbacks. In Net, our IO layer implements subscribers to handle writes, closes and flushes.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Subscription</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor-stream, reactor-net</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.rx.subscription.*, reactor.io.net.impl.*</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">In Stream, we offer optimized PushSubscriptions and buffering-ready ReactiveSubscription. In Net, our Async IO reader-side use custom Subscriptions to implement backpressure.</p></td>
</tr>
</tbody>
</table>
<div class="paragraph">
<p>We have worked with the standard since the inception of Reactor 2 and progressed in our journey until the <strong>1.0.0</strong> was about to release.
It is now available on <em>Maven Central</em> and other popular mirrors. You will also find it as a <strong>transitive dependency to reactor-core</strong>.</p>
</div>
</div>
<div class="sect2">
<h3 id="rx">Reactive Extensions</h3>
<div class="paragraph">
<p>Reactive Extensions, or more commonly <a href="https://msdn.microsoft.com/en-gb/data/gg577609.aspx">Rx</a>,
are a set of well-defined Functional APIs extending the Observer pattern to an epic scale.</p>
</div>
<div class="ulist">
<div class="title">Rx patterns support implementing Reactive data sequences handling with a few design keys:</div>
<ul>
<li>
<p>Abstract the time/latency away with a callback chain: only called when data is available</p>
</li>
<li>
<p>Abstract the threading model away: Synchronous or Asynchronous it is just an <em>Observable</em> / <em>Stream</em> we deal with</p>
</li>
<li>
<p>Control error-passing and terminations: error and complete signals in addition to the data payload signal are passed to the chain</p>
</li>
<li>
<p>Solve multiple scatter-aggregation and other composition issues in various predefined API.</p>
</li>
</ul>
</div>
<div class="paragraph">
<p>The standard implementation of Reactive Extensions in the JVM is <a href="https://github.com/ReactiveX/RxJava">RxJava</a>.
It provides a powerful functional API and ports mostly all the concept over from the original Microsoft library.</p>
</div>
<div class="paragraph">
<p>Reactor 2 provides a <a href="#streams">specific module</a> implementing a subset of the documented Reactive Extensions and on a very few occasion adapting the name
to match our specific behavior. This focused approach around data-centric issues (microbatching, composition&#8230;&#8203;) is depending on
Reactor <a href="#core-functional">Functional</a> units, <a href="#core-dispatchers">Dispatchers</a> and the <a href="#reactivestreams">Reactive Streams</a> contract.
We encourage users who need the full flavor of Reactive Extensions to try out RxJava and <a href="https://github.com/ReactiveX/RxJavaReactiveStreams">bridge with us</a>.
In the end the user can benefit from powerful asynchronous and IO capacities provided by Reactor while composing with the complete RxJava ecosystem.</p>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
Some operations, behaviors, and the immediate understanding of Reactive Streams are still unique to Reactor as of now and we will try to flesh out
the unique features in the <a href="#streams">appropriate section</a>.
</td>
</tr>
</table>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
<a href="#net-overview">Async IO</a> capabilities are also depending on <em>Stream Capacity</em> for
backpressure and auto-flush options.
</td>
</tr>
</table>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 2. Misalignments between Rx and Reactor Streams</caption>
<colgroup>
<col style="width: 33%;">
<col style="width: 33%;">
<col style="width: 33%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top">rx</th>
<th class="tableblock halign-left valign-top">reactor-stream</th>
<th class="tableblock halign-left valign-top">Comment</th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Observable</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.rx.Stream</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Reflect the implementation of the Reactive Stream Publisher</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Operator</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.rx.action.Action</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Reflect the implementation of the Reactive Stream Processor</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Observable with 1 data at most</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.rx.Promise</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Type a unique result, reflect the implementation of the Reactive Stream Processor and provides for optional asynchronous dispatching.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Factory API (just, from, merge&#8230;&#8203;.)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.rx.Streams</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Aligned with a core data-focused subset, return Stream</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Functional API (map, filter, take&#8230;&#8203;.)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.rx.Stream</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Aligned with a core data-focused subset, return Stream</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Schedulers</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">reactor.core.Dispatcher, org.reactivestreams.Processor</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Reactor Streams compute operations with unbounded shared Dispatchers or bounded Processors</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Observable.observeOn()</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Stream.dispatchOn()</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Just an adapted naming for the dispatcher argument</p></td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
<h1 id="reactor-core" class="sect0"><strong>reactor-core</strong></h1>
<div class="openblock partintro">
<div class="content">
<div class="quoteblock">
<blockquote>
You should never do your asynchronous work alone.
</blockquote>
<div class="attribution">
&#8212; Jon Brisbin<br>
<cite>After writing Reactor 1</cite>
</div>
</div>
<div class="quoteblock">
<blockquote>
You should never do your asynchronous work alone.
</blockquote>
<div class="attribution">
&#8212; Stephane Maldini<br>
<cite>After writing Reactor 2</cite>
</div>
</div>
<div class="listingblock">
<div class="title">Head first with a Groovy example of some Core work</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="groovy"><span class="comment">//Initialize context and get default dispatcher</span>
Environment.initialize()

<span class="comment">//RingBufferDispatcher with 8192 slots by default</span>
<span class="keyword">def</span> dispatcher = Environment.sharedDispatcher()

<span class="comment">//Create a callback</span>
Consumer&lt;<span class="predefined-type">Integer</span>&gt; c = { data -&gt;
        println <span class="string"><span class="delimiter">&quot;</span><span class="content">some data arrived: </span><span class="inline"><span class="inline-delimiter">$</span>data</span><span class="delimiter">&quot;</span></span>
}

<span class="comment">//Create an error callback</span>
Consumer&lt;<span class="predefined-type">Throwable</span>&gt; errorHandler = { <span class="local-variable">it</span>.printStackTrace }

<span class="comment">//Dispatch data asynchronously</span>
dispatcher.dispatch(<span class="integer">1234</span>, c, errorHandler)

Environment.terminate()</code></pre>
</div>
</div>
<div class="listingblock">
<div class="title">A second taster, the Reactive Streams way</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="groovy"><span class="comment">//standalone async processor</span>
<span class="keyword">def</span> processor = RingBufferProcessor.&lt;<span class="predefined-type">Integer</span>&gt;create()

<span class="comment">//send data, will be kept safe until a subscriber attaches to the processor</span>
processor.onNext(<span class="integer">1234</span>)
processor.onNext(<span class="integer">5678</span>)

<span class="comment">//consume integer data</span>
processor.subscribe(<span class="keyword">new</span> Subscriber&lt;<span class="predefined-type">Integer</span>&gt;(){

  <span class="type">void</span> onSubscribe(Subscription s){
    <span class="comment">//unbounded subscriber</span>
    s.request <span class="predefined-type">Long</span>.MAX
  }

  <span class="type">void</span> onNext(<span class="predefined-type">Integer</span> data){
    println data
  }

  <span class="type">void</span> onError(<span class="predefined-type">Throwable</span> err){
    err.printStackTrace()
  }

  <span class="type">void</span> onComplete(){
    println <span class="string"><span class="delimiter">'</span><span class="content">done!</span><span class="delimiter">'</span></span>
  }
}

<span class="comment">//Shutdown internal thread and call complete</span>
processor.onComplete()</code></pre>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="_core_overview">Core Overview</h2>
<div class="sectionbody">
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/core-overview.png"><img src="images/core-overview.png" alt="Core Overview" width="650"></a>
</div>
<div class="title">Figure 5. How Doge can use Reactor-Core</div>
</div>
<div class="paragraph">
<p><strong>Reactor Core</strong> has the following artefacts:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p><strong>Common IO &amp; functional types</strong>, some directly backported from Java 8 Functional Interfaces</p>
<div class="ulist">
<ul>
<li>
<p>Function, Supplier, Consumer, Predicate, BiConsumer, BiFunction</p>
</li>
<li>
<p>Tuples</p>
</li>
<li>
<p>Resource, Pausable, Timer</p>
</li>
<li>
<p>Buffer, Codec and a handful of predifined Codecs</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Environment</strong> context</p>
</li>
<li>
<p><strong>Dispatcher</strong> contract and a handful of predefined Dispatchers</p>
</li>
<li>
<p>Predefined <strong>Reactive Streams Processor</strong></p>
</li>
</ul>
</div>
</div>
</div>
<div class="paragraph">
<p>Alone, reactor-core can already be used as a drop-in replacement for another Message-Passing strategy, to schedule timed tasks or to organize your code in small functional blocks implementing the Java 8 backport interfaces.
Such breakdown allows to play more nicely with other Reactive libraries especially removing the burden of understanding the RingBuffer for the impatient developer.</p>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
Reactor-Core implicitely <em>shadows</em> LMAX Disruptor, so it won&#8217;t appear nor collide with an existing Disruptor dependency
</td>
</tr>
</table>
</div>
</div>
</div>
<div class="sect1">
<h2 id="core-functional">Functional Artefacts</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Functional reusable blocks are core and mostly a required artefact to use as soon as you get into Reactor. <span class="footnote" id="_footnote_disclaimer">[<a id="_footnoteref_1" class="footnote" href="#_footnote_1" title="View footnote.">1</a>]</span>
So what&#8217;s cool about Functional Programming ? One of the core ideas is to start treating executable code as a data like another. <span class="footnote" id="_footnote_disclaimer">[<a id="_footnoteref_2" class="footnote" href="#_footnote_2" title="View footnote.">2</a>]</span>
To some extent it is akin to the concept of Closures or Anonymous Functions, where business logic can be decided by the original caller.
It also avoids loads of imperative IF/SWITCH blocks and makes a clear separation of concerns: each block achieves one purpose and doesn&#8217;t need to share anything.</p>
</div>
<div class="sect2">
<h3 id="_organizing_functional_blocks">Organizing Functional Blocks</h3>
<div class="paragraph">
<p>Every Functional component gives the explicit intent of its general mission:</p>
</div>
<div class="ulist">
<ul>
<li>
<p><a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/main/java/reactor/fn/Consumer.java">Consumer</a>: simple callback - fire-and-forget</p>
</li>
<li>
<p><a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/main/java/reactor/fn/BiConsumer.java">BiConsumer</a>: simple callback with two arguments (often used in sequence comparaisons, e.g. previous and next arguments)</p>
</li>
<li>
<p><a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/main/java/reactor/fn/Function.java">Function</a>: transforming logic - request/reply</p>
</li>
<li>
<p><a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/main/java/reactor/fn/Consumer.java">BiFunction</a>: transforming with two arguments (often used in accumulators, comparing previous and next arguments then returning a new value)</p>
</li>
<li>
<p><a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/main/java/reactor/fn/Supplier.java">Supplier</a>: factory logic - polling</p>
</li>
<li>
<p><a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/main/java/reactor/fn/Predicate.java">Predicate</a>: testing logic - filtering</p>
</li>
</ul>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
We consider Publisher and Subscriber interfaces also <strong>functional blocks</strong>, dare we say <em>Reactive Functional Blocks</em>.
Nevertheless they are the basic components used everywhere around in Reactor and Beyond. Stream API will usually accept <strong>reactor.fn</strong> arguments to create on your behalf the appropriate Subscribers.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">The good news about wrapping executable instructions within Functional artefacts is that you can reuse them like <strong>Lego Bricks</strong>.</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Consumer&lt;<span class="predefined-type">String</span>&gt; consumer = <span class="keyword">new</span> Consumer&lt;<span class="predefined-type">String</span>&gt;(){
        <span class="annotation">@Override</span>
        <span class="type">void</span> accept(<span class="predefined-type">String</span> value){
                <span class="predefined-type">System</span>.out.println(value);
        }
};

<span class="comment">//Now in Java 8 style for brievety</span>
Function&lt;<span class="predefined-type">Integer</span>, <span class="predefined-type">String</span>&gt; transformation = integer -&gt; <span class="string"><span class="delimiter">&quot;</span><span class="delimiter">&quot;</span></span>+integer;

Supplier&lt;<span class="predefined-type">Integer</span>&gt; supplier = () -&gt; <span class="integer">123</span>;

BiConsumer&lt;Consumer&lt;<span class="predefined-type">String</span>&gt;, <span class="predefined-type">String</span>&gt; biConsumer = (callback, value) -&gt; {
        <span class="keyword">for</span>(<span class="type">int</span> i = <span class="integer">0</span>; i &lt; <span class="integer">10</span>; i++){
                <span class="comment">//lazy evaluate the final logic to run</span>
                callback.accept(value);
        }
};

<span class="comment">//note how the execution flows from supplier to biconsumer</span>
biConsumer.accept(
        consumer,
        transformation.apply(
                supplier.get()
        )
);</code></pre>
</div>
</div>
<div class="paragraph">
<p>It might not sound like a striking revolution at first, however this basic mindset change will reveal precious for
our mission to make asynchronous code sane and composable. The Dispatchers will use Consumer for their typed Data and Error callbacks.
The Reactor Streams module will use all these artifacts for greater good as well.</p>
</div>
<div class="admonitionblock tip">
<table>
<tr>
<td class="icon">
<i class="fa icon-tip" title="Tip"></i>
</td>
<td class="content">
A good practice when using an IoC container such as Spring is to leverage the <a href="https://docs.spring.io/spring/docs/current/spring-framework-reference/html/beans.html#beans-java">Java Configuration</a> feature to return stateless Functional Beans.
Then injecting the blocks in a Stream pipeline or dispatching their execution becomes quite elegant.
</td>
</tr>
</table>
</div>
</div>
<div class="sect2">
<h3 id="_tuples">Tuples</h3>
<div class="paragraph">
<p>You might have noticed these interfaces are strongly typed with Generic support and a small fixed number of argument.
So how do you pass more than 1 or 2 arguments ? The answer is in one class : <strong>Tuple</strong>.
Tuples are like typed CSV lines in a single object instance, you want them in functional programming to keep both the type safety and a variable number of arguments.</p>
</div>
<div class="paragraph">
<p>Let&#8217;s take the previous example and try replacing the double-argument BiConsumer with a single-argument Consumer:</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Consumer&lt;Tuple2&lt;Consumer&lt;<span class="predefined-type">String</span>&gt;, <span class="predefined-type">String</span>&gt;&gt; biConsumer = tuple -&gt; {
        <span class="keyword">for</span>(<span class="type">int</span> i = <span class="integer">0</span>; i &lt; <span class="integer">10</span>; i++){
                <span class="comment">//Correct typing, compiler happy</span>
                tuple.getT1().accept(tuple.getT2());
        }
};

biConsumer.accept(
        Tuple.of(
                consumer,
                transformation.apply(supplier.get())
        )
);</code></pre>
</div>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
Tuples involve a bit more allocation, and that&#8217;s why the common use cases of comparison or keyed signals are handled with Bi*<strong>*</strong> artifacts directly.
</td>
</tr>
</table>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="core-dispatchers">Environment and Dispatchers</h2>
<div class="sectionbody">
<div class="paragraph">
<p>The functional building blocks in place, we can start playing asynchronously with them. First stop is bringing us to the Dispatcher section.</p>
</div>
<div class="paragraph">
<p>Before we can start any Dispatcher, we want to make sure we create them efficiently. Usually Dispatchers are expensive to create as they will
pre-allocate a segment of memory to hold the dispatched signals, the famous runtime vs startup trade-off introduced in the preface.
A specific shared context named <strong>Environment</strong> has been introduced to manage these various dispatchers, thus avoiding inapproriate creations.</p>
</div>
<div class="sect2">
<h3 id="_environment">Environment</h3>
<div class="paragraph">
<p>Environments are created and terminated by the reactor user (or by the extension library if available, e.g. <em>@Spring</em>).
They automatically read a configuration file located in <a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/main/resources/META-INF/reactor/reactor-environment.properties">META_INF/reactor/reactor-environment.properties</a>.</p>
</div>
<div class="admonitionblock tip">
<table>
<tr>
<td class="icon">
<i class="fa icon-tip" title="Tip"></i>
</td>
<td class="content">
Properties file can be tuned at runtime by providing under the classpath location <em>META-INF/reactor</em> a desired new properties configuration.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">There switching from the default configuration at runtime is achieved by passing the followying Environment Variable: <em>reactor.profiles.active</em>.</div>
<div class="content">
<pre>java - jar reactor-app.jar -Dreactor.profiles.active=turbo</pre>
</div>
</div>
<div class="listingblock">
<div class="title">Starting and Terminating the Environment</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Environment env = Environment.initialize();

<span class="comment">//Current registered environment is the same than the one initialized</span>
Assert.isTrue(Environment.get() == env);

<span class="comment">//Find a dispatcher named &quot;shared&quot;</span>
Dispatcher d  = Environment.dispatcher(<span class="string"><span class="delimiter">&quot;</span><span class="content">shared</span><span class="delimiter">&quot;</span></span>);

<span class="comment">//get the Timer bound to this environment</span>
<span class="predefined-type">Timer</span> timer = Environment.timer();

<span class="comment">//Shutdown registered Dispatchers and Timers that might run non-daemon threads</span>
Environment.terminate();
<span class="comment">//An option could be to register a shutdownHook to automatically invoke terminate.</span></code></pre>
</div>
</div>
<div class="admonitionblock tip">
<table>
<tr>
<td class="icon">
<i class="fa icon-tip" title="Tip"></i>
</td>
<td class="content">
It&#8217;s best to try maintaining a single Environment alive for a given JVM application. Use of <em>Environment.initializeIfEmpty()</em> will be prefered most of the time.
</td>
</tr>
</table>
</div>
</div>
<div class="sect2">
<h3 id="_dispatchers">Dispatchers</h3>
<div class="paragraph">
<p>Dispatchers are there since Reactor 1, they abstract away the mean of message-passing in a common contract similar to the Java Executor.
In fact they do extend Executor!</p>
</div>
<div class="paragraph">
<p>The Dispatcher contract offers a strongly typed way to pass a signal with its Data and Error <strong>Consumers</strong> executed (a)synchronously.
This way we fix a first issue faced by classic Executors, the error isolation. In effect instead of interrupting the assigned resource,
the Error Consumer will be invoked. If none has been provided it will try to find an existing Environment and use its assigned <em>errorJournalConsumer</em>.</p>
</div>
<div class="paragraph">
<p>A second unique feature offered by the asynchronous Dispatcher is to allow for reentrant dispatching by using a <em>Tail Recurse</em> strategy.
Tail Recursion is used when dispatch detects the dispatcher classLoader has been assigned to the running thread and if so, enqueue the task to be executed when the current consumer returns.</p>
</div>
<div class="listingblock">
<div class="title">Using a synchronous and a multi-threaded dispatcher like in this <a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/test/groovy/reactor/core/dispatch/DispatcherSpec.groovy">Groovy Spock test</a>:</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="groovy"><span class="keyword">import</span> <span class="include">reactor.core.dispatch.*</span>

<span class="comment">//...</span>

<span class="key">given</span>:
  <span class="keyword">def</span> sameThread = <span class="keyword">new</span> SynchronousDispatcher()
  <span class="keyword">def</span> diffThread = <span class="keyword">new</span> ThreadPoolExecutorDispatcher(<span class="integer">1</span>, <span class="integer">128</span>)
  <span class="keyword">def</span> currentThread = <span class="predefined-type">Thread</span>.currentThread()
  <span class="predefined-type">Thread</span> taskThread = <span class="predefined-constant">null</span>

  <span class="keyword">def</span> consumer = { ev -&gt;
    taskThread = <span class="predefined-type">Thread</span>.currentThread()
  }

  <span class="keyword">def</span> errorConsumer = { error -&gt;
    error.printStackTrace()
  }

<span class="key">when</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">a task is submitted</span><span class="delimiter">&quot;</span></span>
  sameThread.dispatch(<span class="string"><span class="delimiter">'</span><span class="content">test</span><span class="delimiter">'</span></span>, consumer, errorConsumer)

<span class="key">then</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">the task thread should be the current thread</span><span class="delimiter">&quot;</span></span>
  currentThread == taskThread

<span class="key">when</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">a task is submitted to the thread pool dispatcher</span><span class="delimiter">&quot;</span></span>
  <span class="keyword">def</span> latch = <span class="keyword">new</span> <span class="predefined-type">CountDownLatch</span>(<span class="integer">1</span>)
  diffThread.dispatch(<span class="string"><span class="delimiter">'</span><span class="content">test</span><span class="delimiter">'</span></span>, { ev -&gt; consumer(ev); latch.countDown() }, errorConsumer)

  latch.await(<span class="integer">5</span>, <span class="predefined-type">TimeUnit</span>.SECONDS) <span class="comment">// Wait for task to execute</span>

<span class="key">then</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">the task thread should be different when the current thread</span><span class="delimiter">&quot;</span></span>
  taskThread != currentThread</code></pre>
</div>
</div>
<div class="admonitionblock warning">
<table>
<tr>
<td class="icon">
<i class="fa icon-warning" title="Warning"></i>
</td>
<td class="content">
Like the Executor they will miss a feature that we will add along the 2.x release line: Reactive Streams protocol.
They are ones of the few leftovers in Reactor that are not directly tied to the Reactive Streams standard directly. However,
they can be combined with the Reactor Stream to quickly fix that as we will explore in the <a href="#streams">Stream Section</a>.
Essentially that means a user can directly hit them until they eventually and temporarely block since the capacity might be bounded by most Dispatcher implementations.
</td>
</tr>
</table>
</div>
<table class="tableblock frame-all grid-all">
<caption class="title">Table 3. An introduction to the Dispatcher family</caption>
<colgroup>
<col>
<col>
<col>
<col>
<col>
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top">Dispatcher</th>
<th class="tableblock halign-left valign-top">From Environment</th>
<th class="tableblock halign-left valign-top">Description</th>
<th class="tableblock halign-left valign-top">Strengths</th>
<th class="tableblock halign-left valign-top">Weaknesses</th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>RingBuffer</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">sharedDispatcher()</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><a href="https://lmax-exchange.github.io/disruptor/">An LMAX Disruptor</a> RingBuffer based Dispatcher.</p></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Small latency peaks tolerated</p>
</div>
<div class="paragraph">
<p>Fastest Async Dispatcher, 10-15M+ dispatch/sec on commodity hardware</p>
</div>
<div class="paragraph">
<p>Support ordering</p>
</div></div></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>'Spin' Loop when getting the next slot on full capcity</p>
</div>
<div class="paragraph">
<p>Single Threaded, no concurrent dispatch</p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>Mpsc</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">sharedDispatcher() if Unsafe not available</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Alternative optimized message-passing structure.</p></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Latency peaks tolerated</p>
</div>
<div class="paragraph">
<p>5-10M+ dispatch/sec on commodity hardware</p>
</div>
<div class="paragraph">
<p>Support ordering</p>
</div></div></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Unbounded and possibly using as much available heap memory as possible</p>
</div>
<div class="paragraph">
<p>Single Threaded, no concurrent dispatch</p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>WorkQueue</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">workDispatcher()</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><a href="https://lmax-exchange.github.io/disruptor/">An LMAX Disruptor</a> RingBuffer based Dispatcher.</p></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Latency Peak tolerated for a limited time</p>
</div>
<div class="paragraph">
<p>Fastest Multi-Threaded Dispatcher, 5-10M+ dispatch/sec on commodity hardware</p>
</div></div></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>'Spin' Loop when getting the next slot on full capcity</p>
</div>
<div class="paragraph">
<p>Concurrent dispatch</p>
</div>
<div class="paragraph">
<p>Doesn&#8217;t support ordering</p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><strong>Synchronous</strong></p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">dispatcher("sync") or SynchronousDispatcher.
INSTANCE</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Runs on the current thread.</p></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Upstream and Consumer executions are colocated</p>
</div>
<div class="paragraph">
<p>Useful for Test support</p>
</div>
<div class="paragraph">
<p>Support ordering if the reentrant dispatch is on the current thread</p>
</div></div></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>No Tail Recursion support</p>
</div>
<div class="paragraph">
<p>Blocking</p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">TailRecurse</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">tailRecurse() or TailRecurse
Dispatcher.
INSTANCE</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Synchronous Reentrant Dispatcher that enqueue dispatches when currently dispatching.</p></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Upstream and Consumer executions are colocated</p>
</div>
<div class="paragraph">
<p>Reduce execution stack, greatly expanded by functional call chains</p>
</div></div></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Unbounded Tail Recurse depth</p>
</div>
<div class="paragraph">
<p>Blocking</p>
</div>
<div class="paragraph">
<p>Support ordering (Thread Stealing)</p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">ThreadPoolExecutor</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">newDispatcher(int, int, DispatcherType.
THREAD_POOL_EXECUTOR)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Use underlying ThreadPoolExecutor message-passing</p></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Multi-Threaded</p>
</div>
<div class="paragraph">
<p>Blocking Consumers, permanent latency tolerated</p>
</div>
<div class="paragraph">
<p>1-5M+ dispatch/sec on commodity hardware</p>
</div></div></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Concurrent run on a given consumer executed twice or more</p>
</div>
<div class="paragraph">
<p>Unbounded by default</p>
</div>
<div class="paragraph">
<p>Doesn&#8217;t support ordering</p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Traceable
Delegating</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Decorate an existing dispatcher with TRACE level logs.</p></td>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p>Dispatch tapping</p>
</div>
<div class="paragraph">
<p>Runs slower than the delegated dispatcher alone</p>
</div></div></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Log overhead (runtime, disk)</p></td>
</tr>
</tbody>
</table>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/rbd2.png"><img src="images/rbd2.png" alt="Ring Buffer message passing" width="500"></a>
</div>
<div class="title">Figure 6. RingBufferDispatcher at a given time T</div>
</div>
</div>
<div class="sect2">
<h3 id="_dispatchersupplier">DispatcherSupplier</h3>
<div class="paragraph">
<p>You may have noticed some Dispatchers are single-threaded, especially the <code>RingBufferDispatcher</code> and <code>MpscDispatcher</code>.
Going further, refering to the Reactive Stream specification, the Subscriber/Processor implementation should not allow for
concurrent notifications. This impacts Reactor <code>Streams</code> in particular, and trying to use <code>Stream.dispatchOn(Dispatcher)</code> with a
Dispatcher that leaves the door open to concurrent signals will fail explicitely.</p>
</div>
<div class="paragraph">
<p>There is however a way to workaround that limitation by using pools of Dispatcher or <strong>DispatcherSupplier</strong>. In effect, as a <code>Supplier</code> factory, the indirection offered by
<code>Supplier.get()</code> to retrieve a Dispatcher allow for interesting pooling strategy : RoundRobin, Least-Used&#8230;&#8203;</p>
</div>
<div class="paragraph">
<p><code>Environment</code> offers static helpers to create, and eventually register against the current active <code>Environment</code> pools of Dispatchers:
groups of RoundRobin returned Dispatchers. Once ready, suppliers will provide for a controlled number of Dispatchers.</p>
</div>
<div class="listingblock">
<div class="title">As usual with Dispatchers, <code>Environment</code> is the one-stop shop to manage them:</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Environment.initialize();
<span class="comment">//....</span>

<span class="comment">//Create an anonymous pool of 2 dispatchers with automatic default settings (same type than default dispatcher, default backlog size...)</span>
DispatcherSupplier supplier = Environment.newCachedDispatchers(<span class="integer">2</span>);

Dispatcher d1 = supplier.get();
Dispatcher d2 = supplier.get();
Dispatcher d3 = supplier.get();
Dispatcher d4 = supplier.get();

Assert.isTrue( d1 == d3  &amp;&amp; d2 == d4);
supplier.shutdown();

<span class="comment">//Create and register a new pool of 3 dispatchers</span>
DispatcherSupplier supplier1 = Environment.newCachedDispatchers(<span class="integer">3</span>, <span class="string"><span class="delimiter">&quot;</span><span class="content">myPool</span><span class="delimiter">&quot;</span></span>);
DispatcherSupplier supplier2 = Environment.cachedDispatchers(<span class="string"><span class="delimiter">&quot;</span><span class="content">myPool</span><span class="delimiter">&quot;</span></span>);

Assert.isTrue( supplier1 == supplier2 );
supplier1.shutdown();</code></pre>
</div>
</div>
</div>
<div class="sect2">
<h3 id="_timers">Timers</h3>
<div class="paragraph">
<p>Dispatchers compute incoming tasks as soon as possible. Timers however come with periodic and one-time scheduling API.
Reactor Core offers an <code>HashWheelTimer</code> by default and it is automatically bound to any new Environment.
HashWheelTimers are perfect for dealing with massive concurrent in-memory scheduled tasks, it&#8217;s a powerful alternative to Java <code>TaskScheduler</code>.</p>
</div>
<div class="admonitionblock warning">
<table>
<tr>
<td class="icon">
<i class="fa icon-warning" title="Warning"></i>
</td>
<td class="content">
While it is suited for windowing (mini tasks periods under the minute order of magnitude), it is not a resilient scheduler since all tasks are lost when the application shutdowns.
</td>
</tr>
</table>
</div>
<div class="admonitionblock tip">
<table>
<tr>
<td class="icon">
<i class="fa icon-tip" title="Tip"></i>
</td>
<td class="content">
Timers will receive some attention along the next releases, e.g. we would love to add persisting/shared scheduling support with Redis.
Please voice your opinion or propose any contribution here!
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">A simple timer creation as seen in one of our <a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/test/groovy/reactor/fn/timer/HashWheelTimerYieldingStrategy.groovy">Groovy Spock test</a>:</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="groovy"><span class="keyword">import</span> <span class="include">reactor.fn.timer.Timer</span>

<span class="comment">//...</span>

<span class="key">given</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">a new timer</span><span class="delimiter">&quot;</span></span>
    Environment.initializeIfEmpty()
    <span class="predefined-type">Timer</span> timer = Environment.timer()
    <span class="keyword">def</span> latch = <span class="keyword">new</span> <span class="predefined-type">CountDownLatch</span>(<span class="integer">10</span>)

<span class="key">when</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">a task is submitted</span><span class="delimiter">&quot;</span></span>
    timer.schedule(
            { <span class="predefined-type">Long</span> now -&gt; latch.countDown() } <span class="keyword">as</span> Consumer&lt;<span class="predefined-type">Long</span>&gt;,
            period,
            <span class="predefined-type">TimeUnit</span>.MILLISECONDS
    )

<span class="key">then</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">the latch was counted down</span><span class="delimiter">&quot;</span></span>
    latch.await(<span class="integer">1</span>, <span class="predefined-type">TimeUnit</span>.SECONDS)
    timer.cancel()
    Environment.terminate()</code></pre>
</div>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="core-processor">Core Processors</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Core Processors are here to do a more focused job than Dispatchers:
Computing asynchronous tasks <strong>with back-pressure support</strong>.</p>
</div>
<div class="paragraph">
<p>They also play nicely with other <strong>Reactive Streams</strong> vendors since they directly implement the <a href="https://github.com/reactive-streams/reactive-streams-jvm/blob/master/api/src/main/java/org/reactivestreams/Processor.java">org.reactivestreams.Processor</a> interface.
Remember that a Processor is both a Subscriber AND a Publisher, so you can insert it in a Reactive Streams chain where you wish (source, processing, sink).</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
The specification doesn&#8217;t recommend specifically to hit <code>Processor.onNext(d)</code> directly. We do offer that support but the backpressure will of course not be propagated except with eventual blocking.
One can explicitely use an anonymous Subscription to pass first to a Processor using Processor.onSubscribe to get the backpressure feedback within the implemented request method.
</td>
</tr>
</table>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
OnNext must be serialized e.g. coming from a single thread at a time (no concurrent <em>onXXX</em> signal is allowed). However Reactor supports it if the Processors are created using the conventioned <code>Processor.share()</code> method, e.g. <code>RingBufferProcessor.share()</code>.
This decision must be taken at creation time in order to use the right coordination logic within the implementation, so choose wisely: <em>is this going to be a a standard publishing sequence</em> (no concurrent) or is this going to be <em>hit by multiple threads</em> ?
</td>
</tr>
</table>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">Reactor makes a single exception to the standard when it comes to the specific XXXX <strong>Work</strong> Processor artefacts:</div>
<div class="ulist">
<ul>
<li>
<p>Usually Reactive Streams Processor will dispatch the same sequence data asynchronously to all Subscribers subscribed at a given time T. It&#8217;s akin to <strong>Publish/Subscribe</strong> pattern.</p>
</li>
<li>
<p><strong>WorkProcessors</strong> will distribute the data to its convenience, making the most of each Subscriber. That means Subscribers at a given time T will always see distinct data. It&#8217;s akin to <strong>WorkQueue</strong> pattern.</p>
</li>
</ul>
</div>
</div>
</div>
<div class="paragraph">
<p>We expect to increase our collection of Core Processors over the 2.x release line.</p>
</div>
</div>
</div>
<div class="sect1">
<h2 id="_ringbuffer_processors">RingBuffer Processors</h2>
<div class="sectionbody">
<div class="paragraph">
<p>RingBuffer-based Reactive Streams Processors are good for a bunch of #awesome reasons:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>Über high throughput</p>
</li>
<li>
<p>Replay from the latest not consumed data</p>
<div class="ulist">
<ul>
<li>
<p>If no Subscriber is listening, data won&#8217;t be lost (unlike <code>Broadcaster</code> from Reactor-Stream).</p>
</li>
<li>
<p>If a Subscriber cancels during processing, signal will be safely replayed, it actually works nicely with the <a href="#rbwp-note">RingBufferWorkProcessor</a></p>
</li>
</ul>
</div>
</li>
<li>
<p>Smart back-pressure, it allows for a bounded size anytime and the subscribers have the responsibility to consume and request more data</p>
</li>
<li>
<p>Propagated back-pressure, since it&#8217;s a Processor, it can be subscribed to pass the information along</p>
</li>
<li>
<p>Multi-threaded inbound/outbound Processor capabilities</p>
</li>
</ul>
</div>
<h3 id="_actually_ringbuffer_processor_are_like_typed_code_micromessagebroker_code" class="discrete">Actually RingBuffer*Processor are like typed <code>MicroMessageBroker</code> !</h3>
<div class="paragraph">
<p>Their only drawbacks is they might be costly at runtime to create and they can&#8217;t be shared as easily as its cousin <code>RingBufferDispatcher</code>.
That makes them suited for High-Throughput Pre-defined Data Pipelines.</p>
</div>
<div class="sect2">
<h3 id="core-rbp">RingBufferProcessor</h3>
<div class="paragraph">
<p>Reactor&#8217;s <a href="/docs/api/index.html?reactor/core/processor/RingBufferProcessor.html">RingBufferProcessor</a> component is essentially a <a href="https://github.com/LMAX-Exchange/disruptor">Disruptor RingBuffer</a> adapted to the Reactive Streams API. Its purpose is to provide as close to bare-metal efficiency as possible. It is intended for situations where you need to dispatch tasks onto another thread with extremely low overhead and extremely high throughput and manage backpressure in your workflow.</p>
</div>
<div class="quoteblock">
<blockquote>
I use RingBufferProcessor to compute various output remote calls asynchronously: AMQP, SSD storage and an In-Memory store,
the variable latency is totally eaten by the Processor and our Million-Message-Per-Sec Datasource never blocks !
</blockquote>
<div class="attribution">
&#8212; Happy Reactor user<br>
<cite>Use Case for RingBufferProcessor</cite>
</div>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/RBP.png"><img src="images/RBP.png" alt="Ring Buffer message passing" width="650"></a>
</div>
<div class="title">Figure 7. RingBufferProcessor at a given time T, with 2 Subscribers, all consuming the same sequence, but delta consuming rate is allowed until the ring buffer is full. This will happen when blue cube is colliding with its next clockwise yellow cube.</div>
</div>
<div class="paragraph">
<p>To create a <code>RingBufferProcessor</code>, you use static <code>create</code> helper methods.</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Processor&lt;<span class="predefined-type">Integer</span>, <span class="predefined-type">Integer</span>&gt; p = RingBufferProcessor.create(<span class="string"><span class="delimiter">&quot;</span><span class="content">test</span><span class="delimiter">&quot;</span></span>, <span class="integer">32</span>); <i class="conum" data-value="1"></i><b>(1)</b>
Stream&lt;<span class="predefined-type">Integer</span>&gt; s = Streams.wrap(p); <i class="conum" data-value="2"></i><b>(2)</b>

s.consume(i -&gt; <span class="predefined-type">System</span>.out.println(<span class="predefined-type">Thread</span>.currentThread() + <span class="string"><span class="delimiter">&quot;</span><span class="content"> data=</span><span class="delimiter">&quot;</span></span> + i)); <i class="conum" data-value="3"></i><b>(3)</b>
s.consume(i -&gt; <span class="predefined-type">System</span>.out.println(<span class="predefined-type">Thread</span>.currentThread() + <span class="string"><span class="delimiter">&quot;</span><span class="content"> data=</span><span class="delimiter">&quot;</span></span> + i)); <i class="conum" data-value="4"></i><b>(4)</b>
s.consume(i -&gt; <span class="predefined-type">System</span>.out.println(<span class="predefined-type">Thread</span>.currentThread() + <span class="string"><span class="delimiter">&quot;</span><span class="content"> data=</span><span class="delimiter">&quot;</span></span> + i)); <i class="conum" data-value="5"></i><b>(5)</b>

input.subscribe(p); <i class="conum" data-value="6"></i><b>(6)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Create a <code>Processor</code> with an internal RingBuffer capacity of 32 slots.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Create a Reactor <code>Stream</code> from this Reactive Streams <code>Processor</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Each call to <code>consume</code> creates a Disruptor <code>EventProcessor</code> on its own <code>Thread</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Each call to <code>consume</code> creates a Disruptor <code>EventProcessor</code> on its own <code>Thread</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="5"></i><b>5</b></td>
<td>Each call to <code>consume</code> creates a Disruptor <code>EventProcessor</code> on its own <code>Thread</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="6"></i><b>6</b></td>
<td>Subscribe this <code>Processor</code> to a Reactive Streams <code>Publisher</code>.</td>
</tr>
</table>
</div>
<div class="paragraph">
<p>Each element of data passed to the Processor&#8217;s <code>Subscribe.onNext(Buffer)</code> method will be "broadcast" to all consumers. There&#8217;s no round-robin distribution with this <code>Processor</code> because that&#8217;s in the <code>RingBufferWorkProcessor</code>, discussed below. If you passed the integers 1, 2 and 3 into the <code>Processor</code>, you would see output in the console similar to this:</p>
</div>
<div class="listingblock">
<div class="content">
<pre>Thread[test-2,5,main] data=1
Thread[test-1,5,main] data=1
Thread[test-3,5,main] data=1
Thread[test-1,5,main] data=2
Thread[test-2,5,main] data=2
Thread[test-1,5,main] data=3
Thread[test-3,5,main] data=2
Thread[test-2,5,main] data=3
Thread[test-3,5,main] data=3</pre>
</div>
</div>
<div class="paragraph">
<p>Each thread is receiving all values passed into the <code>Processor</code> and each thread gets the values in an ordered way since it&#8217;s using the <code>RingBuffer</code> internally to manage the slots available to publish values.</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
RingBufferProcessor can replay missed signals -0 subscribers- to any future subscribers. That will force a processor to wait onNext() if a full buffer is not being drained by a subscriber.
From the last sequence acknowledged by a subsUp to the size of the configured ringbuffer will be kept ready to be replayed for every new subscriber, even if the event has already been sent (FanOut).
</td>
</tr>
</table>
</div>
</div>
<div class="sect2">
<h3 id="work">RingBufferWorkProcessor</h3>
<div class="paragraph">
<p>Unlike the standard <code>RingBufferProcessor</code>, which broadcasts its values to all consumers, the <code>RingBufferWorkProcessor</code> partitions the incoming values based on the number of consumers. Values come into the <code>Processor</code> and are sent to the various threads (because each consumer has its own thread) in a round-robin fashion, while still using the internal <code>RingBuffer</code> to efficiently manage the publication of values by providing backpressure to the producer when appropriate.</p>
</div>
<div class="quoteblock">
<blockquote>
We implemented a RingBufferWorkProcessor to scale-up and load-balance various HTTP microservices calls. I might be wrong but it looks like its faster than light (!) and the GC pressure is totally under control.
</blockquote>
<div class="attribution">
&#8212; Happy Reactor user<br>
<cite>Use Case for RingBufferWorkProcessor</cite>
</div>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/RBWP.png"><img src="images/RBWP.png" alt="Ring Buffer message passing" width="650"></a>
</div>
<div class="title">Figure 8. RingBufferWorkProcessor at a given time T, with 2 Subscribers, each consuming unique sequence (availabilty FIFO), delta consuming rate is allowed until the ring buffer is full. This will happen when blue cube is colliding with its next clockwise yellow cube.</div>
</div>
<div class="paragraph">
<p>To use the <code>RingBufferWorkProcessor</code>, the only thing you have to change from the above code sample is the reference to the static <code>create</code> method. You&#8217;ll use the one on the <code>RingBufferWorkProcessor</code> class itself instead. The rest of the code remains identical.</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Processor&lt;<span class="predefined-type">Integer</span>, <span class="predefined-type">Integer</span>&gt; p = RingBufferWorkProcessor.create(<span class="string"><span class="delimiter">&quot;</span><span class="content">test</span><span class="delimiter">&quot;</span></span>, <span class="integer">32</span>); <i class="conum" data-value="1"></i><b>(1)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Create a <code>Processor</code> with an internal RingBuffer capacity of 32 slots.</td>
</tr>
</table>
</div>
<div class="paragraph">
<p>Now when values are published to the <code>Processor</code>, they will not be broadcast to every consumer, but be partitioned based on the number of consumers. When we run this sample, we see output like this now:</p>
</div>
<div class="listingblock">
<div class="content">
<pre>Thread[test-2,5,main] data=3
Thread[test-3,5,main] data=2
Thread[test-1,5,main] data=1</pre>
</div>
</div>
<div id="rbwp-note" class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
RingBufferWorkProcessor can replay interrupted signals, detecting <code>CancelException</code> from the terminating subscriber. It will be the only case where a signal will
actually be played eventually once more with another Subscriber. <strong>We guarantee at-least-once delivery for any events</strong>.
If you are familiar with semantic you might now say "Wait, this RingBufferWorkProcessor works like a Message Broker?", and the answer is yes.
</td>
</tr>
</table>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="core-codecs">Codecs and Buffer</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Byte manipulation is a core concern that applies to a lot of data pipeline configurations.
It is extensively used by <a href="#net-overview">reactor-net</a> to marshall and unmarshall bytes received or sent over IO.</p>
</div>
<div class="paragraph">
<p>The <code>reactor.io.buffer.Buffer</code> is a decorator for Java <code>ByteBuffer</code> handling, adding a series of operations. The goal is to minimize
byte copy by playing with the ByteBuffer limits and reading or overwritting pre-allocated bytes. Tracking the ByteBuffer positions can
quickly switch the developer brain into headache mode. At least it did that to us and we just decided to propose this simple tool to our users.</p>
</div>
<div class="listingblock">
<div class="title">A simple Buffer manipulation as seen in one of our <a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/test/groovy/reactor/io/buffer/BufferSpec.groovy">Groovy Spock test</a>:</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="groovy"><span class="keyword">import</span> <span class="include">reactor.io.buffer.Buffer</span>

<span class="comment">//...</span>

<span class="key">given</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">an empty Buffer and a full Buffer</span><span class="delimiter">&quot;</span></span>
                <span class="keyword">def</span> buff = <span class="keyword">new</span> <span class="predefined-type">Buffer</span>()
                <span class="keyword">def</span> fullBuff = <span class="predefined-type">Buffer</span>.wrap(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello World!</span><span class="delimiter">&quot;</span></span>)

<span class="key">when</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">a Buffer is appended</span><span class="delimiter">&quot;</span></span>
                buff.append(fullBuff)

<span class="key">then</span>: <span class="string"><span class="delimiter">&quot;</span><span class="content">the Buffer was added</span><span class="delimiter">&quot;</span></span>
                buff.position() == <span class="integer">12</span>
                buff.flip().asString() == <span class="string"><span class="delimiter">&quot;</span><span class="content">Hello World!</span><span class="delimiter">&quot;</span></span></code></pre>
</div>
</div>
<div class="paragraph">
<p>A useful application for Buffer is <code>Buffer.View</code>, which is returned by multiple operations such as <code>split()</code>.
It simply provides for a copy-free way to scan and introspect bytes from ByteBuffer. Buffer.View is also a kind of <code>Buffer</code>, so
the same operations are exposed.</p>
</div>
<div class="listingblock">
<div class="title">Reusing the same bytes for chunked read using a delimiter and <code>Buffer.View</code>:</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="type">byte</span> delimiter = (<span class="type">byte</span>) <span class="string"><span class="delimiter">'</span><span class="content">;</span><span class="delimiter">'</span></span>;
<span class="type">byte</span> innerDelimiter = (<span class="type">byte</span>) <span class="string"><span class="delimiter">'</span><span class="content">,</span><span class="delimiter">'</span></span>;

<span class="predefined-type">Buffer</span> buffer = <span class="predefined-type">Buffer</span>.wrap(<span class="string"><span class="delimiter">&quot;</span><span class="content">a;b-1,b-2;c;d;</span><span class="delimiter">&quot;</span></span>);

<span class="predefined-type">List</span>&lt;<span class="predefined-type">Buffer</span>.View&gt; views = buffer.split(delimiter);

<span class="type">int</span> viewCount = views.size();
Assert.isTrue(viewCount == <span class="integer">4</span>);

<span class="keyword">for</span> (<span class="predefined-type">Buffer</span>.View view : views) {
    <span class="predefined-type">System</span>.out.println(view.get().asString()); <span class="comment">//prints &quot;a&quot; then &quot;b-1,b-2&quot;, then &quot;c&quot; and finally &quot;d&quot;</span>

    <span class="keyword">if</span>(view.indexOf(innerDelimiter) != -<span class="integer">1</span>){
      <span class="keyword">for</span>(<span class="predefined-type">Buffer</span>.View innerView : view.get().split(innerDelimiter)){
        <span class="predefined-type">System</span>.out.println(innerView.get().asString()); <span class="comment">//prints &quot;b-1&quot; and &quot;b-2&quot;</span>
      }
    }
}</code></pre>
</div>
</div>
<div class="paragraph">
<p>Playing with <code>Buffer</code> can feel a bit low-level for the common marshalling/unmarshalling use cases and Reactor comes with a series of pre-defined converters called <code>Codec</code>.
Some <code>Codec</code> will be requiring the appropriate extra dependency in the classpath to work, like <a href="https://github.com/FasterXML/jackson/">Jackson</a> for JSON manipulation.</p>
</div>
<div class="paragraph">
<p><code>Codec</code> works in two ways, first it implements <code>Function</code> to encode anything directly and return the encoded data, usually under the form of Buffer.
This is great but it does <strong>only work with stateless Codecs</strong>, the alternative is to use the returned encoding function from <code>Codec.encoder()</code>.</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">Codec.encoder() vs Codec.apply(Source)</div>
<div class="ulist">
<ul>
<li>
<p><code>Codec.encoder()</code> returns a unique encoding function that should not be shared between different Threads.</p>
</li>
<li>
<p><code>Codec.apply()</code> directly encodes (and save an encoder allocation), but the Codec itself should be shared between Threads in that case</p>
</li>
</ul>
</div>
</div>
</div>
<div class="admonitionblock tip">
<table>
<tr>
<td class="icon">
<i class="fa icon-tip" title="Tip"></i>
</td>
<td class="content">
<a href="#net-overview">Reactor Net</a> handles that difference for you in fact by calling <code>Codec.encoder</code> for each new connection.
</td>
</tr>
</table>
</div>
<div class="paragraph">
<p><code>Codec</code> can also decode data into from source type, usually Buffer for most of the Codec implementations. To decode a source data, we must
retrieve a decoding function from <code>Codec.decoder()</code>. Unlike in the encoding side, there isn&#8217;t any apply shortcut as the method is already overloaded for the encoding purpose.
Like the encoding side, the decoding function should not be shared between Threads.</p>
</div>
<div class="paragraph">
<p>There are two forms of <code>Codec.decoder()</code> functions, one will simply return the decoded data where <code>Codec.decoder(Consumer)</code> will call the passed consumer on each decoding event.</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">Codec.decoder() vs Codec.decoder(Consumer)</div>
<div class="ulist">
<ul>
<li>
<p><code>Codec.decoder()</code> is a blocking decoding function, it will return directly the decoded data from the passed source.</p>
</li>
<li>
<p><code>Codec.decoder(Consumer)</code> can be used for non-blocking decoding, it will return nothing (null) and only invoke the passed Consumer once decoded. It can be combined with any asynchronous facility.</p>
</li>
</ul>
</div>
</div>
</div>
<div class="listingblock">
<div class="title">Using one of the predefined Codecs as verified in this <a href="https://github.com/reactor/reactor/blob/master/reactor-core/src/test/groovy/reactor/io/codec/json/JsonCodecSpec.groovy">Groovy Spock test</a>:</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="groovy"><span class="keyword">import</span> <span class="include">reactor.io.json.JsonCodec</span>

<span class="comment">//...</span>

<span class="key">given</span>: <span class="string"><span class="delimiter">'</span><span class="content">A JSON codec</span><span class="delimiter">'</span></span>
                <span class="keyword">def</span> codec = <span class="keyword">new</span> JsonCodec&lt;<span class="predefined-type">Map</span>&lt;<span class="predefined-type">String</span>, <span class="predefined-type">Object</span>&gt;, <span class="predefined-type">Object</span>&gt;(<span class="predefined-type">Map</span>);
    <span class="keyword">def</span> latch = <span class="keyword">new</span> <span class="predefined-type">CountDownLatch</span>(<span class="integer">1</span>)

<span class="key">when</span>: <span class="string"><span class="delimiter">'</span><span class="content">The decoder is passed some JSON</span><span class="delimiter">'</span></span>
                <span class="predefined-type">Map</span>&lt;<span class="predefined-type">String</span>, <span class="predefined-type">Object</span>&gt; decoded;
                <span class="keyword">def</span> callbackDecoder = codec.decoder{
                  decoded = <span class="local-variable">it</span>
                  latch.countDown()
                }
                <span class="keyword">def</span> blockingDecoder = codec.decoder()

                <span class="comment">//yes this is real simple async strategy, but that's not the point here :)</span>
                <span class="predefined-type">Thread</span>.start{
                  callbackDecoder.apply(<span class="predefined-type">Buffer</span>.wrap(<span class="string"><span class="delimiter">&quot;</span><span class="content">{</span><span class="char">\&quot;</span><span class="content">a</span><span class="char">\&quot;</span><span class="content">: </span><span class="char">\&quot;</span><span class="content">alpha</span><span class="char">\&quot;</span><span class="content">}</span><span class="delimiter">&quot;</span></span>))
    }

    <span class="keyword">def</span> decodedMap = blockingDecoder.apply(<span class="predefined-type">Buffer</span>.wrap(<span class="string"><span class="delimiter">&quot;</span><span class="content">{</span><span class="char">\&quot;</span><span class="content">a</span><span class="char">\&quot;</span><span class="content">: </span><span class="char">\&quot;</span><span class="content">beta</span><span class="char">\&quot;</span><span class="content">}</span><span class="delimiter">&quot;</span></span>)

<span class="key">then</span>: <span class="string"><span class="delimiter">'</span><span class="content">The decoded maps have the expected entries</span><span class="delimiter">'</span></span>
    latch.await()
                decoded.size() == <span class="integer">1</span>
                decoded[<span class="string"><span class="delimiter">'</span><span class="content">a</span><span class="delimiter">'</span></span>] == <span class="string"><span class="delimiter">'</span><span class="content">alpha</span><span class="delimiter">'</span></span>
                decodedMap[<span class="string"><span class="delimiter">'</span><span class="content">a</span><span class="delimiter">'</span></span>] == <span class="string"><span class="delimiter">'</span><span class="content">beta</span><span class="delimiter">'</span></span></code></pre>
</div>
</div>
<table class="tableblock frame-all grid-all">
<caption class="title">Table 4. Available Core Codecs:</caption>
<colgroup>
<col>
<col>
<col>
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top">Name</th>
<th class="tableblock halign-left valign-top">Description</th>
<th class="tableblock halign-left valign-top">Required Dependency</th>
</tr>
</thead>
<tbody>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">ByteArrayCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Wrap/unwrap byte arrays from/to Buffer.</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">DelimitedCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Split/Aggregate Buffer and delegate to the passed Codec for unit marshalling.</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">FrameCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Split/Aggregate Buffer into <code>Frame</code> Buffers according to successive prefix lengths.</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">JavaSerializationCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Deserialize/Serialize Buffers using Java Serialization.</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">PassThroughCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Leave the Buffers untouched.</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">StringCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Convert String to/from Buffer</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">LengthFieldCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Find the length and decode/encode the appropriate number of bytes into/from Buffer</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">KryoCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Convert Buffer into Java objects using Kryo with Buffers</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><a href="https://github.com/EsotericSoftware/kryo">com.esotericsoftware.kryo:kryo</a></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">JsonCodec,JacksonJsonCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Convert Buffer into Java objects using Jackson with Buffers</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><a href="https://github.com/FasterXML/jackson">com.fasterxml.jackson.core:jackson-databind</a></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">SnappyCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A Compression Codec which applies a delegate Codec after unpacking/before packing Buffer</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock"><a href="https://xerial.org/snappy-java">org.xerial.snappy:snappy-java</a></p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">GZipCodec</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">A Compression Codec which applies a delegate Codec after unpacking/before packing Buffer</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<h1 id="reactor-stream" class="sect0"><strong>reactor-stream</strong></h1>
<div class="openblock partintro">
<div class="content">
<div class="quoteblock">
<blockquote>
Nope, you shall not use Future.get(), ever.
</blockquote>
<div class="attribution">
&#8212; Stephane Maldini<br>
<cite>with a Banking Sector Customer</cite>
</div>
</div>
<div class="listingblock">
<div class="title">Head first with a Java 8 example of some Stream work</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="keyword">import</span> <span class="include">static</span> <span class="include">reactor.Environment</span>.*;
<span class="keyword">import</span> <span class="include">reactor.rx.Streams</span>;
<span class="keyword">import</span> <span class="include">reactor.rx.BiStreams</span>;

<span class="comment">//...</span>

Environment.initialize()

<span class="comment">//find the top 10 words used in a list of Strings</span>
Streams.from(aListOfString)
  .dispatchOn(sharedDispatcher())
  .flatMap(sentence -&gt;
    Streams
      .from(sentence.split(<span class="string"><span class="delimiter">&quot;</span><span class="content"> </span><span class="delimiter">&quot;</span></span>))
      .dispatchOn(cachedDispatcher())
      .filter(word -&gt; !word.trim().isEmpty())
      .observe(word -&gt; doSomething(word))
  )
  .map(word -&gt; Tuple.of(word, <span class="integer">1</span>))
  .window(<span class="integer">1</span>, <span class="predefined-type">TimeUnit</span>.SECONDS)
  .flatMap(words -&gt;
    BiStreams.reduceByKey(words, (prev, next) -&gt; prev + next)
      .sort((wordWithCountA, wordWithCountB) -&gt; -wordWithCountA.t2.compareTo(wordWithCountB.t2))
      .take(<span class="integer">10</span>)
      .finallyDo(event -&gt; LOG.info(<span class="string"><span class="delimiter">&quot;</span><span class="content">---- window complete! ----</span><span class="delimiter">&quot;</span></span>))
  )
  .consume(
    wordWithCount -&gt; LOG.info(wordWithCount.t1 + <span class="string"><span class="delimiter">&quot;</span><span class="content">: </span><span class="delimiter">&quot;</span></span> + wordWithCount.t2),
    error -&gt; LOG.error(<span class="string"><span class="delimiter">&quot;</span><span class="delimiter">&quot;</span></span>, error)
  );</code></pre>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="streams">Coordinating tasks with Streams and Promises</h2>
<div class="sectionbody">
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/streams-overview.png"><img src="images/streams-overview.png" alt="Stream Overview" width="650"></a>
</div>
<div class="title">Figure 9. How Doge can use Reactor-Stream</div>
</div>
<div class="paragraph">
<p><strong>Reactor Streams</strong> has the following artifacts:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p><code>Stream</code> and its direct implementations</p>
<div class="ulist">
<ul>
<li>
<p>Contains <strong>reactive extensions</strong> and other composition API</p>
</li>
</ul>
</div>
</li>
<li>
<p><code>Promise</code> with a specific <a href="https://promisesaplus.com">A+ flavored</a> API</p>
<div class="ulist">
<ul>
<li>
<p>Can be transformed back to Stream with <code>Promise.stream()</code></p>
</li>
</ul>
</div>
</li>
<li>
<p>Static <strong>Factories</strong>, the one-stop-shops to create related components</p>
<div class="ulist">
<ul>
<li>
<p><code>Streams</code> for <code>Stream</code> creation from well-defined data sources (Iterable, nothing, Future, Publisher&#8230;&#8203;)</p>
</li>
<li>
<p><code>BiStreams</code> for key-value <code>Stream&lt;Tuple2&gt;</code> processing (reduceByKey&#8230;&#8203;)</p>
</li>
<li>
<p><code>IOStreams</code> for <a href="#streams-persistent">Persisting</a> and <a href="#core-codecs">Decoding</a> <code>Streams</code></p>
</li>
<li>
<p><code>Promises</code> for single-data-only <code>Promise</code></p>
</li>
</ul>
</div>
</li>
<li>
<p><code>Action</code> and its direct implementations of every operation provided by the <code>Stream</code> following the <strong>Reactive Streams Processor</strong> specification</p>
<div class="ulist">
<ul>
<li>
<p>Not created directly, but with the Stream API (<code>Stream.map()</code> &#8594; MapAction, <code>Stream.filter()</code> &#8594; FilterAction&#8230;&#8203;)</p>
</li>
</ul>
</div>
</li>
<li>
<p><code>Broadcaster</code>, a specific kind of <code>Action</code> exposing onXXXX interfaces for dynamic data dispatch</p>
<div class="ulist">
<ul>
<li>
<p>Unlike <a href="#core-processor">Core Processors</a>, they will usually not bother with buffering data if there is no subscriber attached</p>
</li>
<li>
<p>However the <code>BehaviorBroadcaster</code> can replay the latest signal to new Subscribers</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
Do not confuse <code>reactor.rx.Stream</code> with the new JDK 8 <code>java.util.stream.Stream</code>. The latter does not offer a Reactive Streams based API nor Reactive Extensions. However, the JDK 8 <code>Stream</code> API is quite complete when used with primitive types and Collections. In fact it&#8217;s quite interesting for JDK 8 enabled applications to mix both JDK and Reactive Streams.
</td>
</tr>
</table>
</div>
</div>
</div>
<div class="sect1">
<h2 id="streams-basics">Streams Basics</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Reactor offers <code>Stream</code> or <code>Promise</code> based on the Reactive Streams standard to compose statically typed data pipelines.</p>
</div>
<div class="paragraph">
<p>It is an incredibly useful and flexible component. It&#8217;s flexible enough to be used to just compose asynchronous actions together like RxJava&#8217;s <code>Observable</code>. But it&#8217;s powerful enough it can function as an asynchronous work queue that forks and joins arbitrary compositions or other Reactive Streams components coming from one of the other implementors of the standard.<span class="footnote" id="_footnote_reactive-streams-implementors">[<a id="_footnoteref_3" class="footnote" href="#_footnote_3" title="View footnote.">3</a>]</span>.</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">There are basically two rough categories of streams</div>
<div class="ulist">
<ul>
<li>
<p>A <strong>hot</strong> <code>Stream</code> is unbounded and capable of accepting input data like a sink.</p>
<div class="ulist">
<ul>
<li>
<p>Think <strong>UI events</strong> such as <em>mouse clicks</em> or realtime <strong>feeds</strong> such as <em>sensors</em>, <em>trade positions</em> or <em>Twitter</em>.</p>
</li>
<li>
<p>Adapted backpressure strategies mixed with the Reactive Streams protocol will apply</p>
</li>
</ul>
</div>
</li>
<li>
<p>A <strong>cold</strong> <code>Stream</code> is bounded and generally created from a fixed collection of data like a <code>List</code> or other <code>Iterable</code>.</p>
<div class="ulist">
<ul>
<li>
<p>Think <strong>Cursored Read</strong> such as <em>IO reads</em>, <em>database queries</em>,</p>
</li>
<li>
<p>Automatic Reactive Streams backpressure will apply</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
<div class="paragraph">
<p>As seen <a href="#core-dispatchers">previously</a>, Reactor uses an <code>Environment</code> to keep sets of <code>Dispatcher</code> instances around for shared use in a given JVM (and classloader). An <code>Environment</code> instance can be created and passed around in an application to avoid classloading segregation issues or the static helpers can be used. Throughout the examples on this site, we&#8217;ll use the static helpers and encourage you to do likewise. To do that, you&#8217;ll need to initialize the static <code>Environment</code> somewhere in your application.</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="directive">static</span> {
  Environment.initialize();
}</code></pre>
</div>
</div>
</td>
</tr>
</table>
</div>
</div>
</div>
<div class="sect1">
<h2 id="_creating_streams_and_promises">Creating Streams and Promises</h2>
<div class="sectionbody">
<div class="paragraph">
<p>This is where you start if you are the owner of the data-source and want to just make it Reactive with direct access to various <em>Reactive Extensions</em> and <em>Reactive Streams</em> capacities.</p>
</div>
<div class="paragraph">
<p>Sometimes it&#8217;s also a case for expanding an existing <strong>Reactive Stream Publisher</strong> with <code>Stream</code> API and we fortunately offer one-shot static API to proceed to the conversion.</p>
</div>
<div class="paragraph">
<p>Extending existing Reactor <code>Stream</code> like we do with <code>IterableStream</code>, <code>SingleValueStream</code> etc is also an incentive option to create a <code>Publisher</code> ready source (Stream implements it) injected with Reactor API.</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
<div class="paragraph">
<p>Streams and Promises are relatively inexpensive, our microbenchmark suite succeeds into creating more than 150M/s on commodity hardware.
Most of the Streams stick to the <strong>Share-Nothing</strong> pattern, only creating new immutable objects when required.</p>
</div>
<div class="paragraph">
<p>Every operation will return a new instance:</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Stream&lt;A&gt; stream = Streams.just(a);
Stream&lt;B&gt; transformedStream = stream.map(transformationToB);

Assert.isTrue(transformationStream != stream);
stream.subscribe(subscriber1); <span class="comment">//subscriber1 will see the data A unaltered</span>
transformedStream.subscribe(subscriber2); <span class="comment">//subscriber2 will see the data B after transformation from A.</span>

<span class="comment">//Note theat these two subscribers will materialize independant stream pipelines, a process we also call lifting</span></code></pre>
</div>
</div>
</td>
</tr>
</table>
</div>
<div class="sect2">
<h3 id="_from_cold_data_sources">From Cold Data Sources</h3>
<div class="paragraph">
<p>You can create a <code>Stream</code> from a variety of sources, including an <code>Iterable</code> of known values, a single value to use as the basis for a flow of tasks, or even from blocking structures such as <code>Future</code> of <code>Supplier</code>.</p>
</div>
<div class="listingblock">
<div class="title">Streams.just()</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Stream&lt;<span class="predefined-type">String</span>&gt; st = Streams.just(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello </span><span class="delimiter">&quot;</span></span>, <span class="string"><span class="delimiter">&quot;</span><span class="content">World</span><span class="delimiter">&quot;</span></span>, <span class="string"><span class="delimiter">&quot;</span><span class="content">!</span><span class="delimiter">&quot;</span></span>); <i class="conum" data-value="1"></i><b>(1)</b>

st.dispatchOn(Environment.cachedDispatcher()) <i class="conum" data-value="2"></i><b>(2)</b>
  .map(<span class="predefined-type">String</span>::toUpperCase) <i class="conum" data-value="3"></i><b>(3)</b>
  .consume(s -&gt; <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">%s greeting = %s%n</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Thread</span>.currentThread(), s)); <i class="conum" data-value="4"></i><b>(4)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Create a <code>Stream</code> from a known value but do not assign a default <code>Dispatcher</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td><code>.dispatchOn(Dispatcher)</code> tells the <code>Stream</code> which thread to execute tasks on. Use this to move execution from one thread to another.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Transform the input using a commonly-found convention: the map() method.</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Produce demand on the pipeline, which means "start processing now". It&#8217;s an optimize shortcut for <code>subscribe(Subscriber)</code> where the Subscriber just requests Long.MAX_VALUE by default.</td>
</tr>
</table>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
Cold Data Sources will be replayed from start for every fresh Subscriber passed to <code>Stream.subscribe(Subscriber)</code>, and therefore duplicate consuming is possible.
</td>
</tr>
</table>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 5. Creating pre-determined Streams and Promises</caption>
<colgroup>
<col style="width: 66%;">
<col style="width: 33%;">
</colgroup>
<thead>
<tr>
<th class="tableblock halign-left valign-top">Factory method</th>
<th class="tableblock halign-left valign-top">Data Type</th>
</tr>
</thead>
<tbody>
<tr>
<th class="tableblock halign-center valign-middle" colspan="2"><p class="tableblock">Role</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Streams.&lt;T&gt;empty()</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Only emit <code>onComplete()</code> once <strong>requested by its Subscriber</strong>.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Streams.&lt;T&gt;never()</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Never emit anything. Useful for keep-alive behaviors.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Streams.&lt;T, Throwable&gt;fail(<strong>Throwable</strong>)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Only emit <code>onError(Throwable)</code>.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Streams.from(<strong>Future&lt;T&gt;</strong>)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Block the <code>Subscription.request(long)</code> on the passed <code>Future.get()</code> that might emit <code>onNext(T)</code> and <code>onComplete()</code> otherwise <code>onError(Throwable)</code> for any exception.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Streams.from(<strong>T[]</strong>)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Emit N <code>onNext(T)</code> elements everytime <code>Subscription.request(N)</code> is invoked. If N == Long.MAX_VALUE, emit everything. Once all the array has been read, emit <code>onComplete()</code>.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Streams.from(<strong>Iterable&lt;T&gt;</strong>)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Emit N <code>onNext(T)</code> elements everytime <code>Subscription.request(N)</code> is invoked. If N == Long.MAX_VALUE, emit everything. Once all the array has been read, emit <code>onComplete()</code>.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Streams.range(<strong>long</strong>, <em>long</em>)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Long</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Emit a sequence of N <code>onNext(Long)</code> everytime <code>Subscription.request(N)</code> is invoked. If N == Long.MAX_VALUE, emit everything. Once the inclusive upper bound been read, emit <code>onComplete()</code>.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Streams.just(T, <em>T, T, T, T, T, T, T</em>)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">An optimization over <code>Streams.from(Iterable)</code> that just behaves similarly. Also useful to emit Iterable, Array or Future without colliding with the Streams.from() signatures.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Streams.generate(<strong>Supplier&lt;T&gt;</strong>)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Emit <code>onNext(T)</code> from the producing <code>Supplier.get()</code> factory everytime <code>Subscription.request(N)</code> is called. The demand N is ignored as only one data is emitted. When a null value is returned, emit <code>onComplete()</code>.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Promises.syncTask(Supplier&lt;T&gt;), Promises.task(, Supplier&lt;T&gt;)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Emit a single <code>onNext(T)</code> and <code>onComplete()</code> from the producing <code>Supplier.get()</code> on the first <code>Subscription.request(N)</code> received. The demand N is ignored.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Promises.success(<strong>T</strong>)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Emit <code>onNext(T)</code> and <code>onComplete()</code> whenever a <code>Subscriber</code> is provided to <code>Promise.subscribe(Subscriber)</code>.</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Promises.&lt;T&gt;error(<strong>Throwable</strong>)</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Emit <code>onError(Throwable)</code> whenever a <code>Subscriber</code> is subscribed is provided to <code>Promise.subscribe(Subscriber)</code>.</p></td>
</tr>
</tbody>
</table>
</div>
<div class="sect2">
<h3 id="streams-reactivestreams">From Existing Reactive Publishers</h3>
<div class="paragraph">
<p>Existing Reactive Streams <code>Publishers</code> can very well be from other implementations, including the user ones, or from Reactor itself.</p>
</div>
<div class="paragraph">
<p>The use cases incude:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p><a href="#streams-combine">Combinatory API</a> to coordinate various data sources.</p>
</li>
<li>
<p>Lazy resource access, reading a Data Source on subscribe or on request, e.g. <em>Remote HTTP calls</em>.</p>
</li>
<li>
<p>Data-oriented operations such as Key/Value <code>Tuples Streams</code>, <code>Persistent Streams</code> or Decoding.</p>
</li>
<li>
<p>Plain Publisher decoration with <code>Stream API</code></p>
</li>
</ul>
</div>
</div>
</div>
<div class="listingblock">
<div class="title">Streams.concat() and Streams.wrap() in action</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Processor&lt;<span class="predefined-type">String</span>,<span class="predefined-type">String</span>&gt; processor = RingBufferProcessor.create();

Stream&lt;<span class="predefined-type">String</span>&gt; st1 = Streams.just(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello </span><span class="delimiter">&quot;</span></span>); <i class="conum" data-value="1"></i><b>(1)</b>
Stream&lt;<span class="predefined-type">String</span>&gt; st2 = Streams.just(<span class="string"><span class="delimiter">&quot;</span><span class="content">World </span><span class="delimiter">&quot;</span></span>); <i class="conum" data-value="1"></i><b>(1)</b>
Stream&lt;<span class="predefined-type">String</span>&gt; st3 = Streams.wrap(processor); <i class="conum" data-value="2"></i><b>(2)</b>

Streams.concat(st1, st2, st3) <i class="conum" data-value="3"></i><b>(3)</b>
  .reduce( (prev, next) -&gt; prev + next ) <i class="conum" data-value="4"></i><b>(4)</b>
  .consume(s -&gt; <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">%s greeting = %s%n</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Thread</span>.currentThread(), s)); <i class="conum" data-value="5"></i><b>(5)</b>

processor.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">!</span><span class="delimiter">&quot;</span></span>);
processor.onComplete();</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Create a <code>Stream</code> from a known value.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Decorate the core processor with <code>Stream</code> API. Note that <code>Streams.concat()</code> would have accepted the processor directly as a valid Publisher argument.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Concat the 3 upstream sources (all st1, then all st2, then all st3).</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Accumulate the input 2 by 2 and emit the result on upstream completion, after the last complete from st3.</td>
</tr>
<tr>
<td><i class="conum" data-value="5"></i><b>5</b></td>
<td>Produce demand on the pipeline, which means "start processing now".</td>
</tr>
</table>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 6. Creating from available Reactive Streams Publishers</caption>
<colgroup>
<col style="width: 66%;">
<col style="width: 33%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Factory method</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Data Type</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.create(<strong>Publisher&lt;T&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Only subscribe to the passed <code>Publisher</code> when the first <code>Subscription.request(N)</code> hits the returned <code>Stream</code>.
Therefore it supports malformed Publishers that do not invoke <code>Subscriber.onSubscribe(Subscription)</code> as required per specification.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.wrap(<strong>Publisher&lt;T&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">A simple delegating <code>Stream</code> to the passed <code>Publisher.subscribe(Subscriber&lt;T&gt;)</code> argument. Only supports <em>well formed</em> Publishers correctly using the Reactive Streams protocol:
</p><p class="tableblock">onSubscribe &gt; onNext\* &gt; (onError | onComplete)</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.defer(<strong>Supplier&lt;Publisher&lt;T&gt;&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">A lazy Publisher access using the level of indirection provided by <code>Supplier.get()</code> everytime <code>Stream.subscribe(Subscriber)</code> is called.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.createWith(<strong>BiConsumer&lt;Long,SubscriberWithContext&lt;T, C&gt;</strong>, <em>Function&lt;Subscriber&lt;T&gt;,C&gt;, Consumer&lt;C&gt;</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">A Stream generator with explicit callbacks for each <code>Subscriber</code> request, start and stop events. similar to <code>Streams.create(Publisher)</code> minus the boilerplate for common use.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.switchOnNext(<strong>Publisher&lt;Publisher&lt;T&gt;&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">A Stream alterning in FIFO order between emitted <code>onNext(Publisher&lt;T&gt;)</code> from the passed Publisher. The signals will result in downstream Subscriber&lt;T&gt; receiving the next Publisher sequence of <code>onNext(T)</code>.
It might interrupt a current upstream emission when the <code>onNext(Publisher&lt;T&gt;)</code> signal is received.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.concat(<strong>Publisher&lt;T&gt;</strong>, <em>Publisher&lt;T&gt;*</em>)
</p><p class="tableblock">Streams.concat(<strong>Publisher&lt;Publisher&lt;T&gt;&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">If a Publisher&lt;T&gt; is already emitting, wait for it to <code>onComplete()</code> before draining the next pending Publisher&lt;T&gt;. As the name suggests its useful to <a href="https://rxmarbles.com/#concat">concat various datasources</a> and keep ordering right.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.merge(<strong>Publisher&lt;T&gt;, Publisher&lt;T&gt;</strong>, Publisher&lt;T&gt;*)
</p><p class="tableblock">Streams.merge(<strong>Publisher&lt;Publisher&lt;T&gt;&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock"><a href="https://rxmarbles.com/#merge">Accept multiple sources</a> and <strong>interleave</strong> their respective sequence. Order won&#8217;t be preserved like with <code>concat</code>. Demand from a Subscriber will be split between various sources with a minimum of 1 to make sure everyone has a chance to send something.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.combineLatest(<strong>Publisher&lt;T1&gt;, Publisher&lt;T2&gt;</strong>, <em>Publisher&lt;T3-N&gt; x6</em>, <strong>Function&lt;Tuple2-N, C&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">C</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock"><a href="https://rxmarbles.com/#combineLatest">Combine most recent emitted elements</a> from the passed sources using the given aggregating <code>Function</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.combineLatest(<strong>Publisher&lt;T1&gt;, Publisher&lt;T2&gt;,</strong> <em>Publisher&lt;T3-N&gt; x6</em>, <strong>Function&lt;Tuple2-N, C&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">C</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock"><a href="https://rxmarbles.com/#zip">Combine most recent elements once</a>, every time a source has emitted a signal, apply the given <code>Function</code> and clear the temporary aggregate. Effectively it&#8217;s a flexible <em>join</em> mechanism for multiple types of sources.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.join(<strong>Publisher&lt;T&gt;, Publisher&lt;T&gt;</strong>, <em>Publisher&lt;T&gt; x6</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">List&lt;T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">A shortcut for zip that only aggregates each complete aggregate in a List matching the order of the passed argument sources.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.await(<strong>Publisher&lt;&gt;</strong>, <em>long, unit, boolean</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">void</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Block the calling thread until <code>onComplete</code> of the passed <code>Publisher</code>. Optional arguments to tune the timeout and the need to request data as well can be passed. It will throw an exception if the final state is <code>onError</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">IOStreams.&lt;K,V&gt;persistentMap(<strong>String</strong>, <em>deleteOnExit</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">V</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock"><a href="#streams-persistent">A simple shortcut over ChronicleStream constructors</a>, a disk-based log appender/tailer. The name argument must match an existing persistent queue under /tmp/persistent-queue\[name\].</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">IOStreams.&lt;K,V&gt;persistentMapReader(<strong>String</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">V</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock"><a href="#streams-persistent">A simple shortcut over ChronicleReaderStream constructors</a>, a disk-based log tailer. The name argument must match an existing persistent queue under /tmp/persistent-queue\[name\].</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">IOStreams.decode(<strong>Codec&lt;SRC, IN, ?&gt;, Publisher&lt;SRC&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">IN</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Use <a href="#core-codecs">Codec decoder</a> to decode the passed source data type into <strong>IN</strong> type.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">BiStreams.reduceByKey(<strong>Publisher&lt;Tuple2&lt;KEY,VALUE&gt;&gt;</strong>, <em>Map&lt;KEY,VALUE&gt;, Publisher&lt;MapStream.Signal&lt;KEY, VALUE&gt;&gt;</em>, <strong>BiFunction&lt;VALUE, VALUE, VALUE&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Tuple2&lt;KEY,VALUE&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">A key-value operation that accumulates computed results for each 2 sequential <code>onNext(VALUE)</code> passed to the <code>BiFunction</code> argument. The result will be released <code>onComplete()</code> only. The options allow to use an existing map store and listen for its events.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">BiStreams.scanByKey(<strong>Publisher&lt;Tuple2&lt;KEY,VALUE&gt;&gt;</strong>, <em>Map&lt;KEY,VALUE&gt;, Publisher&lt;MapStream.Signal&lt;KEY, VALUE&gt;&gt;</em>, <strong>BiFunction&lt;VALUE, VALUE, VALUE&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Tuple2&lt;KEY,VALUE&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">A key-value operation that accumulates computed results for each 2 sequential <code>onNext(VALUE)</code> passed to the <code>BiFunction</code> argument. The result will be released every time just after it has been stored.  The options allow you to use an existing map store and listen for its events.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Promises.when(<strong>Promise&lt;T1&gt;, Promise&lt;T2&gt;</strong>, <em>Promise&lt;T3-N&gt; x6</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">TupleN&lt;T1,T2,\*?&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Join all unique results from <code>Promises</code> and provide for the new <code>Promise</code> with the aggregated <code>Tuple</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Promises.any(<strong>Promise&lt;T&gt;, Promise&lt;T&gt;</strong>, <em>Promise&lt;T&gt; x6</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Pick the first signal available among the passed promises and <code>onNext(T)</code> the returned <code>Promise</code> with this result.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Promises.multiWhen(<strong>Promise&lt;T&gt;, Promise&lt;T&gt;</strong>, <em>Promise&lt;T&gt; x6</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">List&lt;T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Join all unique results from <code>Promises</code> and provide for the new <code>Promise</code> with the aggregated <code>List</code>. The difference with the <code>when</code> alternative is that the type of promises must match.</p></td>
</tr>
</tbody>
</table>
</div>
<div class="sect2">
<h3 id="_from_custom_reactive_publishers">From Custom Reactive Publishers</h3>
<div class="paragraph">
<p>Over time, the Reactor user will become more familiar with <strong>Reactive Streams</strong>. That&#8217;s the perfect moment to start creating custom reactive data-sources!
Usually the implementor would have to respect the specification and verify his work with the <strong>reactive-streams-tck</strong> dependency.
Respecting the contract requires a <strong>Subscription</strong> and a call to <strong>onSubscribe</strong> + a <strong>request(long)</strong> before sending any data.</p>
</div>
<div class="paragraph">
<p>However Reactor allows some flexibility to only deal with the message passing part and will automatically provide the buffering <strong>Subscription</strong> transparently,
the difference is demonstrated in the code sample below.</p>
</div>
<div class="listingblock">
<div class="title">Streams.create and Streams.defer in action</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="directive">final</span> Stream&lt;<span class="predefined-type">String</span>&gt; stream1 = Streams.create(<span class="keyword">new</span> Publisher&lt;<span class="predefined-type">String</span>&gt;() {
  <span class="annotation">@Override</span>
  <span class="directive">public</span> <span class="type">void</span> subscribe(Subscriber&lt;? <span class="local-variable">super</span> <span class="predefined-type">String</span>&gt; sub) {
    sub.onSubscribe(<span class="keyword">new</span> Subscription() { <i class="conum" data-value="1"></i><b>(1)</b>
      <span class="annotation">@Override</span>
      <span class="directive">public</span> <span class="type">void</span> request(<span class="type">long</span> demand) {
        <span class="keyword">if</span>(demand == <span class="integer">2L</span>){
          sub.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">1</span><span class="delimiter">&quot;</span></span>);
          sub.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">2</span><span class="delimiter">&quot;</span></span>);
          sub.onComplete();
        }
      }

      <span class="annotation">@Override</span>
      <span class="directive">public</span> <span class="type">void</span> cancel() {
        <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">Cancelled!</span><span class="delimiter">&quot;</span></span>);
      }
    });
  }
});

<span class="directive">final</span> Stream&lt;<span class="predefined-type">String</span>&gt; stream2 = Streams.create(sub -&gt; {
  sub.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">3</span><span class="delimiter">&quot;</span></span>); <i class="conum" data-value="2"></i><b>(2)</b>
  sub.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">4</span><span class="delimiter">&quot;</span></span>);
  sub.onComplete();
});

<span class="directive">final</span> <span class="predefined-type">AtomicInteger</span> counterSubscriber = <span class="keyword">new</span> <span class="predefined-type">AtomicInteger</span>();

Stream&lt;<span class="predefined-type">String</span>&gt; deferred = Streams.defer(() -&gt; {
  <span class="keyword">if</span> (counterSubscriber.incrementAndGet() == <span class="integer">1</span>) { <i class="conum" data-value="3"></i><b>(3)</b>
    <span class="keyword">return</span> stream1;
  }
  <span class="keyword">else</span> {
     <span class="keyword">return</span> stream2;
  }
});

deferred
  .consume(s -&gt; <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">%s First subscription = %s%n</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Thread</span>.currentThread(), s));
deferred
  .consume(s -&gt; <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">%s Second subscription = %s%n</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Thread</span>.currentThread(), s));</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Create a <code>Stream</code> from a custom valid <code>Publisher</code> which first calls <code>onSubscribe(Subscription)</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Create a <code>Stream</code> from a custom malformed <code>Publisher which skips `onSubscribe(Subscription)</code> and immediately calls <code>onNext(T)</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Create a <code>DeferredStream</code> that will alternate source Publisher&lt;T&gt; on each <code>Stream.subscribe</code> call, evaluating the total number of Subscribers,</td>
</tr>
</table>
</div>
<div class="paragraph">
<p>Where to go from here? There are plenty of use cases that can benefit from a custom Publisher:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p>Reactive Facade to convert any IO call with a matching demand and compose: HTTP calls (read N times), SQL queries (select max N), File reads (read N lines)&#8230;&#8203;</p>
</li>
<li>
<p>Async Facade to convert any hot data callback into a composable API: AMQP Consumer, Spring MessageChannel endpoint&#8230;&#8203;</p>
</li>
</ul>
</div>
</div>
</div>
<div class="paragraph">
<p>Reactor offers some reusable components to avoid the boilerplate checking you would have to do without extending exsiting Stream or <code>PushSubscription</code></p>
</div>
<div class="ulist">
<ul>
<li>
<p>Extending <code>PushSubscription</code> instead of implementing <code>Subscription</code> directly to benefit from terminal state (PushSubscription.isComplete())</p>
</li>
<li>
<p>Using <code>PublisherFactory.create(args)</code> or <code>Streams.createWith(args)</code> to use Functional consumers for every lifecycle step (requested, stopped, started).</p>
</li>
<li>
<p>Extending <code>Stream</code> instead of implementing <code>Publisher</code> directly to benefit from composition API</p>
</li>
</ul>
</div>
<div class="listingblock">
<div class="title">Streams.createWith, an alternative to create() minus some boilerplate</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="directive">final</span> Stream&lt;<span class="predefined-type">String</span>&gt; stream = Streams.createWith(
  (demand, sub) -&gt; { <i class="conum" data-value="1"></i><b>(1)</b>
      sub.context(); <i class="conum" data-value="2"></i><b>(2)</b>
      <span class="keyword">if</span> (demand &gt;= <span class="integer">2L</span> &amp;&amp; !sub.isCancelled()) {
          sub.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">1</span><span class="delimiter">&quot;</span></span>);
          sub.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">2</span><span class="delimiter">&quot;</span></span>);
          sub.onComplete();
      }
  },
  sub -&gt; <span class="integer">0</span>, <i class="conum" data-value="3"></i><b>(3)</b>
  sub -&gt; <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">Cancelled!</span><span class="delimiter">&quot;</span></span>) <i class="conum" data-value="4"></i><b>(4)</b>
);

stream.consume(s -&gt; <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">%s greeting = %s%n</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Thread</span>.currentThread(), s));</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Attach a request consumer reacting on <code>Subscriber</code> requests and passing the demand and the requesting subscriber.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>The <em>sub</em> argument is actually a <code>SubscriberWithContext</code> possibly assigned with some initial state shared by all request callbacks.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Executed once on start, this is also where we initialize the optional shared context; every request callback will receive 0 from <code>context()</code></td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Executed once on any terminal event : <strong>cancel()</strong>, <strong>onComplete()</strong> or <strong>onError(e)</strong>.</td>
</tr>
</table>
</div>
<div class="paragraph">
<p>A good place to start coding the reactive streams way is to simply look at a more elaborate, back-pressure ready <a href="#recipe-filestream">File Stream</a>.</p>
</div>
</div>
<div class="sect2">
<h3 id="_from_hot_data_sources">From Hot Data Sources</h3>
<div class="paragraph">
<p>If you are dealing with an unbounded stream of data like what would be common with a web application that accepts user input via a REST interface, you probably want to use the "hot" variety of <code>Stream</code> in Reactor, which we call a <a href="/docs/api/index.html?reactor/rx/stream/Broadcaster.html">Broadcaster</a>.</p>
</div>
<div class="paragraph">
<p>To use it, you simply declare a pipeline of composable, functional tasks on the <code>Broadcaster</code> and later call <a href="/docs/api/reactor/rx/stream/Broadcaster.html#onNext-O-"><code>Broadcaster.onNext(T)</code></a> to publish values into the pipeline.</p>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
<code>Broadcaster</code> is a valid <code>Processor</code> and <code>Consumer</code>. It&#8217;s possible to <code>onSubscribe</code> a Broadcaster as it&#8217;s also possible to use it as a <code>Consumer</code> delegating <code>Consumer.accept(T)</code> to <code>Broadcaster.onNext(T)</code>.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Broadcaster.create()</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Broadcaster&lt;<span class="predefined-type">String</span>&gt; sink = Broadcaster.create(Environment.get()); <i class="conum" data-value="1"></i><b>(1)</b>

sink.map(<span class="predefined-type">String</span>::toUpperCase) <i class="conum" data-value="2"></i><b>(2)</b>
    .consume(s -&gt; <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">%s greeting = %s%n</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Thread</span>.currentThread(), s)); <i class="conum" data-value="3"></i><b>(3)</b>

sink.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello World!</span><span class="delimiter">&quot;</span></span>); <i class="conum" data-value="4"></i><b>(4)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Create a <code>Broadcaster</code> using the default, shared <code>RingBufferDispatcher</code> as the <code>Dispatcher</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Transform the input using a commonly-found convention: the map() method.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td><code>.consume()</code> is a "terminal" operation, which means it produces demand in Reactive Streams parlance.</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Publish a value into the pipeline, which will cause the tasks to be invoked.</td>
</tr>
</table>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
Hot Data Sources will never be replayed. Subscribers will only see data from the moment they have been passed to <code>Stream.subscribe(Subscriber)</code>.
An exception applies for <code>BehaviorBroadcaster</code> (last emitted element is replayed); <code>Streams.timer()</code> and <code>Streams.period()</code> will also maintain unique timed cursors but will still ignore backpressure.
</td>
</tr>
</table>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
Subscribers will see new data N flowing through a Broadcaster every T+I<sup>N</sup> <strong>only</strong> after they have subscribed at time T.
</td>
</tr>
</table>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 7. Creating flexible Streams</caption>
<colgroup>
<col style="width: 60%;">
<col style="width: 20%;">
<col style="width: 20%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Factory</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Input</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Output</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.timer(<strong>delay</strong>, <em>unit, timer</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Long</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Start a Timer on <code>Stream.subscribe(Subscriber)</code> call and emit a single <code>onNext(0L)</code> then <code>onComplete()</code> once the delay is elapsed. Be sure to pass the optional argument <code>Timer</code> if there is no current active <code>Environment</code>.
<code>Subscription.request(long)</code> will be ignored as no backpressure can apply to a scheduled emission.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.period(<strong>period</strong>, <em>unit, timer</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">N/A</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Long</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Start a Timer on <code>Stream.subscribe(Subscriber)</code> call and every period of time emit <code>onNext(N)</code> where N is an incremented counter starting from 0. Be sure to pass the optional argument <code>Timer</code> if there is no current active <code>Environment</code>.
<code>Subscription.request(long)</code> will be ignored as no backpressure can apply to a scheduled emission.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.&lt;T&gt;switchOnNext()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Publisher&lt;T&gt;</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">An <code>Action</code> which for the record is also a <code>Processor</code>. The <code>onNext(Publisher&lt;T&gt;)</code> signals will result in downstream <code>Subscriber&lt;T&gt;</code> receiving the next Publisher sequence of <code>onNext(T)</code>.
 It might interrupt a current upstream emission when the <code>onNext(Publisher&lt;T&gt;)</code> signal is received.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Broadcaster.&lt;T&gt;create(<em>Environment, Dispatcher</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Create a <em>hot</em> bridge between any context allowed to call <code>onSubscribe</code>, <code>onNext</code>, <code>onComplete</code> or <code>onError</code> and a composable sequence of these signals under a <code>Stream</code>. If no subscribers are actively registered, next signals might trigger a <code>CancelException</code>. The optional <code>Dispatcher</code> and <code>Environment</code> arguments define where to emit each signal. Finally, a Broadcaster can be subscribed any time to a <code>Publisher</code>, like a <code>Stream</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">SerializedBroadcaster.create(<em>Environment, Dispatcher</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Similar to <code>Broadcaster.create()</code> but adds support for concurrent <code>onNext</code> from parallel contexts possibly calling the same broadcaster <code>onXXX</code> methods.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">BehaviorBroadcaster.create(<em>Environment, Dispatcher</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Simlar to <code>Broadcaster.create()</code> but always replays the last data signal (if any) <strong>and</strong> the last terminal signal (<code>onComplete()</code>, <code>onError(Throwable)</code>) to the new Subscribers.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">BehaviorBroadcaster.first(<strong>T</strong>, <em>Environment, Dispatcher</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Similar to <code>BehaviorBroadcaster</code> but starts with a default value T.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.wrap(<strong>Processor&lt;I, O&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">I</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">O</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">A simple delegating <code>Stream</code> to the passed <code>Publisher.subscribe(Subscriber&lt;O&gt;)</code> argument. Only supports <em>well formed</em> Publishers correctly using the Reactive Streams protocol:
</p><p class="tableblock">onSubscribe &gt; onNext\* &gt; (onError | onComplete)</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Promises.&lt;T&gt;prepare(<strong>Environment, Dispatcher</strong>)
</p><p class="tableblock">Promises.ready()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Prepare a <code>Promise</code> ready to be called <strong>exactly once</strong> by any external context through <code>onNext</code>. Since it&#8217;s a stateful container holding the result of the fulfilled promise, new subscribers will immediately run on the current thread.</p></td>
</tr>
</tbody>
</table>
<div class="admonitionblock tip">
<table>
<tr>
<td class="icon">
<i class="fa icon-tip" title="Tip"></i>
</td>
<td class="content">
<div class="paragraph">
<p>For Asynchronous broadcasting, always consider a <a href="#core-processor">Core Processor</a> alternative to a <code>Broadcaster</code>:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p>A Broadcaster will trigger a <a href="https://projectreactor.io/docs/api/reactor/core/processor/CancelException.html">CancelException</a> if there are no subscribers. A Core <code>RingBuffer*Processor</code> will always deliver buffered data to the first subscriber.</p>
</li>
<li>
<p>Some <code>Dispatcher</code> types that can be assigned to a <code>Broadcaster</code> might not support concurrent <code>onNext</code>. Use <code>RingBuffer*Processor.share()</code> for an alternative, thread-safe, concurrent <code>onNext</code>.</p>
</li>
<li>
<p>RingBuffer*Processor supports replaying an event cancelled in-flight by a downstream subscriber if it&#8217;s still running on the processor thread. A Broadcaster won&#8217;t support replaying.</p>
</li>
<li>
<p>RingBuffer*Processor are faster than their alternative Broadcaster with a RingBufferDispatcher</p>
</li>
<li>
<p>RingBufferWorkProcessor supports scaling up with the number of attached subscribers.</p>
</li>
<li>
<p><strong>Broadcaster might be promoted to a <code>Processor</code> in 2.1 anyway, achieving the same thing and removing the need for the Reactor user to struggle picking between <code>Processor</code> and <code>Broadcaster</code></strong>.</p>
</li>
</ul>
</div>
</div>
</div>
</td>
</tr>
</table>
</div>
</div>
<div class="sect2">
<h3 id="wireup">Wiring up a Stream</h3>
<div class="paragraph">
<p>Streams operations&#8201;&#8212;&#8201;except for a few exceptions like terminal actions and <code>broadcast()</code>&#8201;&#8212;&#8201;will never directly subscribe. Instead they will lazily prepare for subscribe.
This is usually called <strong>lift</strong> in Functional programming.</p>
</div>
<div class="paragraph">
<p>That basically means the Reactor <code>Stream</code> user will explicitely call <code>Stream.subscribe(Subscriber)</code> or, alternativly, <strong>terminal</strong> actions such as <code>Stream.consume(Consumer)</code> to materialize all the registered operations.
Before that <code>Actions</code> don&#8217;t really exist. We use <code>Stream.lift(Supplier)</code> to defer the creation of these Actions until <code>Stream.subscribe(Subscriber)</code> is explicitely called.</p>
</div>
<div class="paragraph">
<p>Once everything is wired, each action maintains an upstream <code>Subscription</code> and a downstream <code>Subscription</code> and the Reactive Streams contract applies all along the pipeline.</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
Usually the terminal actions return a <code>Control</code> object instead of <code>Stream</code>.
This is an component you can use to request or cancel a pipeline without being inside a <code>Subscriber</code> context or implementing the full <code>Subscriber</code> contract.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Wiring up 2 pipelines</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="keyword">import</span> <span class="include">static</span> <span class="include">reactor.Environment</span>.*;
<span class="keyword">import</span> <span class="include">reactor.rx.Streams</span>;
<span class="keyword">import</span> <span class="include">reactor.rx.Stream</span>;
<span class="comment">//...</span>

Stream&lt;<span class="predefined-type">String</span>&gt; stream = Streams.just(<span class="string"><span class="delimiter">&quot;</span><span class="content">a</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">b</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">c</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">d</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">e</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">f</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">g</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">h</span><span class="delimiter">&quot;</span></span>);

<span class="comment">//prepare two unique pipelines</span>
Stream&lt;<span class="predefined-type">String</span>&gt; actionChain1 = stream.map(<span class="predefined-type">String</span>::toUpperCase).filter(w -&gt; w.equals(<span class="string"><span class="delimiter">&quot;</span><span class="content">C</span><span class="delimiter">&quot;</span></span>));
Stream&lt;<span class="predefined-type">Long</span>&gt; actionChain2 = stream.dispatchOn(sharedDispatcher()).take(<span class="integer">5</span>).count();

actionChain1.consume(<span class="predefined-type">System</span>.out::println); <span class="comment">//start chain1</span>
<span class="predefined-type">Control</span> c = actionChain2.consume(<span class="predefined-type">System</span>.out::println); <span class="comment">//start chain2</span>
<span class="comment">//...</span>
c.cancel(); <span class="comment">//force this consumer to stop receiving data</span></code></pre>
</div>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/wiringup.png"><img src="images/wiringup.png" alt="The 2 Pipelines wired" width="650"></a>
</div>
<div class="title">Figure 10. After Wiring</div>
</div>
<div class="sect3">
<h4 id="_publish_subscribe">Publish/Subscribe</h4>
<div class="paragraph">
<p>For <strong>Fan-Out</strong> to subscribers from a unified pipeline, <code>Stream.process(Processor)</code>, <code>Stream.broadcast()</code>, <code>Stream.broadcastOn()</code> and <code>Stream.broadcastTo()</code> can be used.</p>
</div>
<div class="listingblock">
<div class="title">Sharing an upstream pipeline and wiring up 2 downstream pipelines</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="keyword">import</span> <span class="include">static</span> <span class="include">reactor.Environment</span>.*;
<span class="keyword">import</span> <span class="include">reactor.rx.Streams</span>;
<span class="keyword">import</span> <span class="include">reactor.rx.Stream</span>;
<span class="comment">//...</span>

Stream&lt;<span class="predefined-type">String</span>&gt; stream = Streams.just(<span class="string"><span class="delimiter">&quot;</span><span class="content">a</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">b</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">c</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">d</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">e</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">f</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">g</span><span class="delimiter">&quot;</span></span>,<span class="string"><span class="delimiter">&quot;</span><span class="content">h</span><span class="delimiter">&quot;</span></span>);

<span class="comment">//prepare a shared pipeline</span>
Stream&lt;<span class="predefined-type">String</span>&gt; sharedStream = stream.observe(<span class="predefined-type">System</span>.out::println).broadcast();

<span class="comment">//prepare two unique pipelines</span>
Stream&lt;<span class="predefined-type">String</span>&gt; actionChain1 = sharedStream.map(<span class="predefined-type">String</span>::toUpperCase).filter(w -&gt; w.equals(<span class="string"><span class="delimiter">&quot;</span><span class="content">C</span><span class="delimiter">&quot;</span></span>));
Stream&lt;<span class="predefined-type">Long</span>&gt; actionChain2 = sharedStream.take(<span class="integer">5</span>).count();

actionChain1.consume(<span class="predefined-type">System</span>.out::println); <span class="comment">//start chain1</span>
actionChain2.consume(<span class="predefined-type">System</span>.out::println); <span class="comment">//start chain2</span></code></pre>
</div>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/broadcast.png"><img src="images/broadcast.png" alt="The 3 Pipelines wired" width="650"></a>
</div>
<div class="title">Figure 11. After Wiring a Shared Stream</div>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 8. Operations considered terminal or explicitely subscribing</caption>
<colgroup>
<col style="width: 66%;">
<col style="width: 33%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt; method</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Return Type</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">subscribe(<strong>Subscriber&lt;T&gt;</strong>)
</p><p class="tableblock"><em>subscribeOn</em></p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">void</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Subscribe the passed <strong>Subscriber&lt;T&gt;</strong> and materialize any pending upstream, wired up lazily (the implicit <strong>lift</strong> for non terminal operation). Note a Subscriber must request data if it expects some. The <code>dispatchOn</code> and <code>subscribeOn</code> alternatives provide for signalling <code>onSubscribe</code> using the passed <code>Dispatcher</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">consume(<em>Consumer&lt;T&gt;,Consumer&lt;T&gt;,Consumer&lt;T&gt;</em>)
</p><p class="tableblock"><em>consumeOn</em></p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Control</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Call <code>subscribe</code> with a <code>ConsumerAction</code> which interacts with each passed <code>Consumer</code>, each time the interest signal is detected. It will <code>request(Streams.capacity())</code> to the received <code>Subscription</code>, which is <code>Long.MAX_VALUE</code> by default, which results in unbounded consuming. The <code>subscribeOn</code> and <code>consumeOn</code> alternatives provide for signalling <code>onSubscribe</code> using the passed <code>Dispatcher</code>. Returns a <code>Control</code> component to cancel the materialized <code>Stream</code>, if necessary. Note that <code>ConsumeAction</code> takes care of unbounded recursion if the <code>onNext(T)</code> signal triggers a blocking request.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">consumeLater()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Control</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Similar to <code>consume</code> but does not fire an initial <code>Subscription.request(long)</code>. The returned <code>Control</code> can be used to <code>request(long)</code> anytime.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">tap()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">TapAndControls</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Similar to <code>consume</code> but returns a <code>TapAndControls</code> that will be dynamically updated each time a new <code>onNext(T)</code> is signalled or cancelled.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">batchConsume(<strong>Consumer&lt;T&gt;</strong>, <em>Consumer&lt;T&gt;, Consumer&lt;T&gt;</em>, <strong>Function&lt;Long,Long&gt;</strong>)
</p><p class="tableblock"><em>batchConsumeOn</em></p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Control</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Similar to <code>consume</code> but will request the mapped <code>Long</code> demand given the previous demand and starting with the default <code>Stream.capacity()</code>. Useful for adapting the demand dynamically due to various factors.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">adaptiveConsume(<strong>Consumer&lt;T&gt;</strong>, <em>Consumer&lt;T&gt;, Consumer&lt;T&gt;</em>, <strong>Function&lt;Stream&lt;Long&gt;,Publisher&lt;Long&gt;&gt;</strong>)
</p><p class="tableblock"><em>adaptiveConsumeOn</em></p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Control</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Similar to <code>batchConsume</code> but will request the computed sequence of demand <code>Long</code>. It can be used to insert flow-control such as <code>Streams.timer()</code> to delay demand.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">next()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Promise&lt;T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Return a <code>Promise&lt;T&gt;</code> that is actively subscribing to the <code>Stream</code>, materializing it, and requesting a single data before unregistering. The immediate next signal <code>onNext(T)</code>, <code>onComplete()</code> or <code>onError(Throwable)</code> will fulfill the promise.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">toList()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Promise&lt;List&lt;T&gt;&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Similar to <code>next()</code> but will wait until the entire sequence has been produced (<code>onComplete()</code>) and pass the accumulated <code>onNext(T)</code> in a single <code>List&lt;T&gt;</code> fulfilling the returned promise.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.toBlockingQueue()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">CompletableBlockingQueue&lt;T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Subscribe to the <code>Stream</code> and return an iterable blocking <code>Queue&lt;T&gt;</code> accumulating all <code>onNext</code> signals. <code>CompletableBlockingQueue.isTerminated()</code> can be used as a condition to exit a blocking <code>poll()</code> loop.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">cache()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Turn any Stream into a <strong>Cold</strong> Stream, able to replay all the sequence of signals individually for each Subscriber.
Due to the unbounded nature of the action, you should probably use it only with small(ish) sequences.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">broadcast()
</p><p class="tableblock">broadcastOn(Environment, Dispatcher)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Turn Any Stream into a <strong>Hot</strong> Stream. This will prevent pipeline duplication by immediately materializing the <code>Stream</code> and be ready to publish the signal to N Subscribers downstream.
The demand will be aggregated from all child Subscribers.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">broadcastTo(<strong>Subscriber&lt;T&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Subscriber&lt;T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">An alternative to <code>Stream.subscribe</code> which allows method chaining since the returned instance is the same as the passed argument.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">process(<strong>Processor&lt;T, O&gt;</strong>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;O&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Similar to broadcast() but accept any given <code>Processor&lt;T, O&gt;</code>. A perfect place to introduce <a href="#core-processor">Core Processors</a> !</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="sect2">
<h3 id="stream-capacity">Setting Capacity</h3>
<div class="paragraph">
<p>The Reactive Streams standard encourages application developers to set reasonable limits on in-flight data. This prevents components from becoming inundated with more data than they can handle, which causes unpredictable problems throughout an application. One of the core concepts of Reactive Streams is that of "backpressure", or the ability of a pipeline to communicate to upstream components that it can only handle a fixed number of items at a time. A useful term to describe this process of queueing and requesting small chunks of a large volume of data is "microbatching".</p>
</div>
<div class="paragraph">
<p>Within a Reactor <code>Stream</code>, it&#8217;s possible to microbatch items to limit the amount of data in-flight at any given time. This has distinct advantages in a number of ways, not the least of which is that it limits exposure to data loss by preventing the system from accepting more data than it can afford to lose if the system was to crash.</p>
</div>
<div class="paragraph">
<p>To limit the amount of data in-flight in a <code>Stream</code>, use the <a href="/docs/api/reactor/rx/Stream.html#capacity-long-"><code>.capacity(long)</code></a> method.</p>
</div>
<div class="listingblock">
<div class="title">Streams.just()</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Stream&lt;<span class="predefined-type">String</span>&gt; st;

st
  .dispatchOn(sharedDispatcher())
  .capacity(<span class="integer">256</span>) <i class="conum" data-value="1"></i><b>(1)</b>
  .consume(s -&gt; service.doWork(s)); <i class="conum" data-value="2"></i><b>(2)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Limit the amount of data in-flight to no more than 256 elements at a time.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Produce demand upstream by requesting the next 256 elements of data.</td>
</tr>
</table>
</div>
<div class="admonitionblock warning">
<table>
<tr>
<td class="icon">
<i class="fa icon-warning" title="Warning"></i>
</td>
<td class="content">
<code>capacity</code> will not affect <code>consume</code> actions if the current Stream dispatcher set with <code>dispatchOn</code> is a <code>SynchronousDispatcher.INSTANCE</code> (default if unset).
</td>
</tr>
</table>
</div>
<div class="admonitionblock tip">
<table>
<tr>
<td class="icon">
<i class="fa icon-tip" title="Tip"></i>
</td>
<td class="content">
We leave as an exercise to the <strong>Reactor User</strong> to study the benefit of setting capacity vs computing dynamic demand with <code>Stream.adaptiveConsume</code> or a custom <code>Subscriber</code>.
</td>
</tr>
</table>
</div>
</div>
<div class="sect2">
<h3 id="_functional_composition">Functional Composition</h3>
<div class="paragraph">
<p>Similar to many other functional libraries, Reactor provides a number of useful methods for composing functions on a <code>Stream</code>. You can passively observe values, transform them from one kind to another, filter out values you don&#8217;t want, buffer values until a size or time trigger is tripped, and many other useful operations.</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
These operations are called <code>Actions</code>, and they will not <a href="#wireup">wire up the <code>Stream</code> directly</a>. They are available on any <code>Stream</code> instance, which means <a href="#streams-basic">you should have one by this stage</a>.
</td>
</tr>
</table>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p><code>Actions</code> are <code>onSubscribe()</code> in declarative order (left to right), so <code>stream.actionA().actionB()</code> will execute actionA first then actionB.</p>
<div class="ulist">
<ul>
<li>
<p><code>onSubscribe()</code> runs on the parent <code>Publisher</code> thread context which can be altered by <code>subscribeOn(Dispatcher)</code> for instance.</p>
</li>
</ul>
</div>
</li>
<li>
<p><code>Actions</code> <code>subscribe()</code> in inverse declarative order (right to left). Whenever <code>subscribe</code> is excplicitely called at the end of the pipeline, <code>subscribe()</code> propagates backward.</p>
<div class="ulist">
<ul>
<li>
<p><code>subscribe()</code> synchronously propagates back which might affect stack size use. If that becomes an issue, use a delegate <code>Processor</code> that runs <code>subscribe()</code> on a <code>Environment.tailRecurse()</code> dispatcher. Then <code>process()</code> it at any point of the chain.</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div>
<div class="sect3">
<h4 id="_observe">Observe</h4>
<div class="paragraph">
<p>If you want to passively observe data as it passes through the pipeline, then use the <code>.observe(Consumer)</code> methods and other <code>reactor.rx.action.passive</code> actions.
To observe values, use <a href="/docs/api/reactor/rx/Stream.html#observe-reactor.fn.Consumer-">.observe(Consumer&lt;? super T&gt;)</a>. To observe errors without dealing with them definitively, use <a href="/docs/api/reactor/rx/Stream.html#observeError-java.lang.Class-reactor.fn.BiConsumer-">.observe(Class&lt;? extends Throwable&gt;, BiConsumer&lt;Object,? extends Throwable&gt;)</a>. To observe the Reactive Streams complete signal, use <a href="/docs/api/reactor/rx/Stream.html#observeComplete-reactor.fn.Consumer-">.observeComplete(Consumer&lt;Void&gt;)</a>. To observe the cancel signal, use <a href="/docs/api/reactor/rx/Stream.html#observeCancel-reactor.fn.Consumer-">.observeCancel(Consumer&lt;Void&gt;)</a>. To observe the Reactive Streams subscribe signal, use <a href="/docs/api/reactor/rx/Stream.html#observeSubscribe-reactor.fn.Consumer-">.observeSubscribe(Consumer&lt;? super Subscription&lt;T&gt;&gt;)</a>.</p>
</div>
<div class="listingblock">
<div class="title">observe(Consumer&lt;T&gt;)</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Stream&lt;<span class="predefined-type">String</span>&gt; st;

st.observe(s -&gt; LOG.info(<span class="string"><span class="delimiter">&quot;</span><span class="content">Got input [{}] on thread [{}}]</span><span class="delimiter">&quot;</span></span>, s, <span class="predefined-type">Thread</span>.currentThread())) <i class="conum" data-value="1"></i><b>(1)</b>
  .observeComplete(v -&gt; LOG.info(<span class="string"><span class="delimiter">&quot;</span><span class="content">Stream is complete</span><span class="delimiter">&quot;</span></span>)) <i class="conum" data-value="2"></i><b>(2)</b>
  .observeError(<span class="predefined-type">Throwable</span>.class, (o, t) -&gt; LOG.error(<span class="string"><span class="delimiter">&quot;</span><span class="content">{} caused an error: {}</span><span class="delimiter">&quot;</span></span>, o, t)) <i class="conum" data-value="3"></i><b>(3)</b>
  .consume(s -&gt; service.doWork(s)); <i class="conum" data-value="4"></i><b>(4)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Passively observe values passing through without producing demand.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Run once all values have been processed and the <code>Stream</code> is marked complete.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Run any time an error is propagated.</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Produce demand on the pipeline and consume any values.</td>
</tr>
</table>
</div>
</div>
<div class="sect3">
<h4 id="_filter">Filter</h4>
<div class="paragraph">
<p>It&#8217;s possible to filter items passing through a <code>Stream</code> so that downstream actions only see the data you want them to see. Filtering actions can be found under the <code>reactor.rx.action.filter</code> package.
The most popular one is the <a href="/docs/api/reactor/rx/Stream.html#filter-reactor.fn.Predicate-"><code>.filter(Predicate&lt;T&gt;)</code></a> method.</p>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
Unmatched data will trigger a <code>Subscription.request(1)</code> if the stream is actually not unbounded with a previous demand of Long.MAX_VALUE.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">filter(Predicate&lt;T&gt;)</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Stream&lt;<span class="predefined-type">String</span>&gt; st;

st.filter(s -&gt; s.startsWith(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello</span><span class="delimiter">&quot;</span></span>)) <i class="conum" data-value="1"></i><b>(1)</b>
  .consume(s -&gt; service.doWork(s)); <i class="conum" data-value="2"></i><b>(2)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>This will only allow values that start with the string <code>'Hello'</code> to pass downstream.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Produce demand on the pipeline and consume any values.</td>
</tr>
</table>
</div>
</div>
<div class="sect3">
<h4 id="_limits">Limits</h4>
<div class="paragraph">
<p>A specific application of filters is for setting limits to a <code>Stream</code>. Limiting actions can be found under the <code>reactor.rx.action.filter</code> package.
There are various ways to tell a Stream&lt;T&gt; its boundary in time, in size and/or on a specific condition.
The most popular one is the <a href="/docs/api/reactor/rx/Stream.html#take-long-"><code>.take(long)</code></a> method.</p>
</div>
<div class="listingblock">
<div class="title">Stream.take(long)</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Streams
  .range(<span class="integer">1</span>, <span class="integer">100</span>)
  .take(<span class="integer">50</span>) <i class="conum" data-value="1"></i><b>(1)</b>
  .consume(
    <span class="predefined-type">System</span>.out::println,
    <span class="predefined-type">Throwable</span>::printStackTrace,
    avoid -&gt; <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">--complete--</span><span class="delimiter">&quot;</span></span>)
  );</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Only take the 50 first elements then cancel upstream and complete downstream.</td>
</tr>
</table>
</div>
</div>
<div class="sect3">
<h4 id="_transformation">Transformation</h4>
<div class="paragraph">
<p>If you want to actively transform data as it passes through the pipeline, then use <code>.map(Function)</code> and other <code>reactor.rx.action.transformation</code> actions.
The most popular transforming action is <a href="/docs/api/reactor/rx/Stream.html#map-reactor.fn.Function-">.map(Function&lt;? super I, ? extends O&gt;)</a>.
A few other <code>Actions</code> depend on transforming data, especially <a href="#streams-combine">Combinatory operations</a> like <code>flatMap</code> or <code>concatMap</code>.</p>
</div>
<div class="listingblock">
<div class="title">Stream.map(Function&lt;T,V&gt;)</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Streams
  .range(<span class="integer">1</span>, <span class="integer">100</span>)
  .map(number -&gt; <span class="string"><span class="delimiter">&quot;</span><span class="delimiter">&quot;</span></span>+number) <i class="conum" data-value="1"></i><b>(1)</b>
  .consume(<span class="predefined-type">System</span>.out::println);</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Transform each Long into a String.</td>
</tr>
</table>
</div>
</div>
<div class="sect3">
<h4 id="stream-flatmap">(A)Sync Transformation: FlatMap, ConcatMap, SwitchMap</h4>
<div class="paragraph">
<p>If you want to execute a distinct pipeline <code>Stream&lt;V&gt;</code> or <code>Publisher&lt;V&gt;</code> given an actual input data, you can use combinatory actions such as <code>.flatMap(Function)</code> and other <code>reactor.rx.action.combination</code> actions.</p>
</div>
<div class="paragraph">
<p>To transform values into a distinct, possibly asynchronous <code>Publisher&lt;V&gt;</code>, use <a href="/docs/api/reactor/rx/Stream.html#map-reactor.fn.Function-">.flatMap(Function&lt;? super I, ? extends Publisher&lt;? extends O&gt;)</a>.
The returned <code>Publisher&lt;V&gt;</code> will then be <strong>merged</strong> back to the main flow signaling <code>onNext(V)</code>. They are properly removed from the merging action whey they complete.
The difference between flatMap, concatMap and switchOnMap is the <strong>merging strategy</strong>, respectively <strong>Interleave</strong>, <strong>Fully Sequential</strong> and <strong>Partially Sequential</strong> (interrupted by <code>onNext(Publisher&lt;T&gt;)</code>).</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
The downstream request is split (minimum 1 by merged Publisher)
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Stream.flatMap(Function)</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Streams
  .range(<span class="integer">1</span>, <span class="integer">100</span>)
  .flatMap(number -&gt; Streams.range(<span class="integer">1</span>, number).subscribeOn(Environment.workDispatcher()) ) <i class="conum" data-value="1"></i><b>(1)</b>
  .consume(
    <span class="predefined-type">System</span>.out::println, <i class="conum" data-value="2"></i><b>(2)</b>
    <span class="predefined-type">Throwable</span>::printStackTrace,
    avoid -&gt; <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">--complete--</span><span class="delimiter">&quot;</span></span>)
  );</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Transform any incoming number into a range of 1-N number merged back and executed on the given Dispatcher.</td>
</tr>
</table>
</div>
</div>
<div class="sect3">
<h4 id="streams-blocking">Blocking and Promises</h4>
<div class="paragraph">
<p>Blocking is considered an anti-pattern in <strong>Reactor</strong>. That said, we do offer an appropriate API (Ah AH!) for integration with legacy operations and for testing support.</p>
</div>
<div class="paragraph">
<p>The Promise API offers a range of <strong>stateful actions</strong> which inspect the current <strong>ready|error|complete</strong> state and, if fulfilled, immediately calls the wired action.</p>
</div>
<div class="listingblock">
<div class="title">Stream.toList()</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Promise&lt;<span class="predefined-type">List</span>&lt;<span class="predefined-type">Long</span>&gt;&gt; result = Streams
  .range(<span class="integer">1</span>, <span class="integer">100</span>)
  .subscribeOn(Environment.workDispatcher())
  .toList(); <i class="conum" data-value="1"></i><b>(1)</b>

<span class="predefined-type">System</span>.out.println(result.await()); <i class="conum" data-value="2"></i><b>(2)</b>
result.onSuccess(<span class="predefined-type">System</span>.out::println); <i class="conum" data-value="3"></i><b>(3)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Consume the entire sequence on the dispatcher thread given in <code>subscribeOn(Dispatcher)</code> operation.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Block (default 30 Seconds) until <code>onComplete()</code> and print only <code>onNext(List&lt;Long&gt;)</code>; or, if <code>onError(e)</code>, wrap as RuntimeException and re-raise.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Since the promise is already fulfilled, <code>System.out.println()</code> will run immediately on the current context.</td>
</tr>
</table>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 9. Waiting for a Stream or Promise</caption>
<colgroup>
<col style="width: 100%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Functional API or Factory method</p></th>
</tr>
<tr>
<td class="tableblock halign-center valign-middle"><div><div class="paragraph">
<p><strong>Role</strong></p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.await(Publisher&lt;?&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Block until the passed Publisher <code>onComplete()</code> or <code>onError(e)</code>, bubbling up the eventual exception.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.next()
</p><p class="tableblock"><em>with</em> Promise.await(), Promise.get()&#8230;&#8203;</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Capture in a Promise the immediate next signal only and <code>onComplete()</code> if the signal was a data. <code>get()</code> can be used to touch but not wait on the promise to fulfill.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.toList()
</p><p class="tableblock"><em>with</em> Promise.await(), Promise.get()&#8230;&#8203;</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Similar to <code>next()</code> but capture the full sequence in a List&lt;T&gt; to fulfill the <code>Promise&lt;List&lt;T&gt;&gt;</code> returned.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.toBlockingQueue()</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Subscribe to the <code>Stream</code> and return an iterable blocking <code>Queue&lt;T&gt;</code> accumulating all <code>onNext</code> signals. <code>CompletableBlockingQueue.isTerminated()</code> can be used as a condition to exit a blocking <code>poll()</code> loop.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Wiring up Synchronous Streams</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">It&#8217;s not specific to any API, but if the current Stream is dispatched on a <code>SynchronousDispatcher</code>, it is actually blocking when a <strong>terminal</strong> action is starting, such as <code>consume()</code>.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="streams-multithreading">Understanding the threading model</h2>
<div class="sectionbody">
<div class="paragraph">
<p>One common purpose for <strong>Reactive Streams</strong> and <strong>Reactive Extensions</strong> is to be unopinionated about threading behavior <strong>thanks to the signal callbacks</strong>.
Streams are all about <strong>it will be executed at some point between now and some time T</strong>. Non-concurrent signals may also preserve <code>Subscriber</code> from concurrency access (share-nothing),
however signals and requests can run on 2 asymmetric threads.</p>
</div>
<div class="paragraph">
<p>By default the <code>Stream</code> is assigned with a <code>SynchronousDispatcher</code> and will inform its immediate child <code>Actions</code> via <code>Stream.getDispatcher()</code>.</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
Various <code>Stream</code> factories, the <code>Broadcaster</code>, the <code>Stream.dispatchOn</code>  and the terminal <code>xxxOn</code> methods might alter the default <code>SynchronousDispatcher</code>.
</td>
</tr>
</table>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">It is fundamental to understand the three major thread switchs available in Reactor Stream:</div>
<div class="ulist">
<ul>
<li>
<p>The <code>Stream.dispatchOn</code> action is the only one available under <code>Stream</code> that will be dispatching <strong>onError</strong>, <strong>onComplete</strong> and <strong>onNext</strong> signals on the given <code>Dispatcher</code>.</p>
<div class="ulist">
<ul>
<li>
<p>Since an action is a <code>Processor</code> it doesn&#8217;t support concurrent <code>Dispatcher</code> such as <code>WorkQueueDispatcher</code>.</p>
</li>
<li>
<p><code>request</code> and <code>cancel</code> will run on the dispatcher as well if in its context already. Otherwise it will execute after the current dispatch ends.</p>
</li>
</ul>
</div>
</li>
<li>
<p>The <code>Stream.subscribeOn</code> action will be executing <strong>onSubscribe</strong> only on the passed dispatcher.</p>
<div class="ulist">
<ul>
<li>
<p>Since the only time the passed <code>Dispatcher</code> is called is <strong>onSubscribe</strong>, any dispatcher can be used including the concurrent ones such as <code>WorkQueueDispatcher</code>.</p>
</li>
<li>
<p>The first <code>request</code> might still execute in the <strong>onSubscribe</strong> thread, for instance with <code>Stream.consume()</code> actions.</p>
</li>
</ul>
</div>
</li>
<li>
<p>Attaching a <code>Processor</code> via <code>Stream.process</code> for instance can affect the thread too. The <code>Processor</code> such as <code>RingBufferProcessor</code> will run the <code>Subscribers</code> on its managed threads.</p>
<div class="ulist">
<ul>
<li>
<p><code>request</code> and <code>cancel</code> will run on the processor as well if in its context already.</p>
</li>
<li>
<p><code>RingBufferWorkProcessor</code> will only dispatch <strong>onNext</strong> signals to one <code>Subscriber</code> at most unless it has cancelled in-flight (replay to a new Subscriber).</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div>
<div class="paragraph">
<p>Since the common contract is to start requesting data <strong>onSubscribe</strong>, <code>subscribeOn</code> is an efficient tool to scale-up streams, particulary unbounded ones.
If a <code>Subscriber</code> requests <strong>Long.MAX_VALUE</strong> in <strong>onSubscribe</strong>, it will then be the only request executed and it will run on the dispatcher assigned in <code>subscribeOn</code>.
This is the default behaviour for unbounded <code>Stream.consume</code> actions.</p>
</div>
<div class="listingblock">
<div class="title">Jumping between threads with an unbounded demand</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Streams
  .range(<span class="integer">1</span>, <span class="integer">100</span>)
  .dispatchOn(Environment.sharedDispatcher()) <i class="conum" data-value="2"></i><b>(2)</b>
  .subscribeOn(Environment.workDispatcher()) <i class="conum" data-value="1"></i><b>(1)</b>
  .consume(); <i class="conum" data-value="3"></i><b>(3)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Assign an <strong>onSubscribe</strong> work queue dispatcher.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Assign a signal <strong>onNext, onError, onComplete</strong> dispatcher.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Consume the <code>Stream</code> <strong>onSubscribe</strong> with <code>Subscription.request(Long.MAX)</code></td>
</tr>
</table>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/longMaxThreading.png"><img src="images/longMaxThreading.png" alt="Unbounded threading" width="600"></a>
</div>
<div class="title">Figure 12. subscribeOn and dispatchOn/process with an unbounded Subscriber</div>
</div>
<div class="paragraph">
<p>However, <code>subscribeOn</code> is less useful when more than 1 request will be involved, like in step-consuming with <code>Stream.capacity(n)</code>.
The only request executed possibly running on the dispatcher assigned in <code>subscribeOn</code> is the <strong>first one</strong>.</p>
</div>
<div class="listingblock">
<div class="title">Jumping between thread with a bounded demand 1</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Streams
  .range(<span class="integer">1</span>, <span class="integer">100</span>)
  .process(RingBufferProcessor.create()) <i class="conum" data-value="2"></i><b>(2)</b>
  .subscribeOn(Environment.workDispatcher()) <i class="conum" data-value="1"></i><b>(1)</b>
  .capacity(<span class="integer">1</span>); <i class="conum" data-value="3"></i><b>(3)</b>
  .consume(); <i class="conum" data-value="4"></i><b>(4)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Assign an <strong>onSubscribe</strong> work queue dispatcher. Note that it is placed after process as the subscribeOn will run on the ringBuffer thread on subscriber and we want to alter it to the work dispatcher.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Assign an async signal <strong>onNext, onError, onComplete</strong> processor. Similar to <code>dispatchOn</code> behavior.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Assign a <code>Stream</code> capacity to 1 so the downstream action adapts</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Consume the <code>Stream</code> <strong>onSubscribe</strong> with <code>Subscription.request(1)</code> and after every 1 <strong>onNext</strong>.</td>
</tr>
</table>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/nThreading.png"><img src="images/nThreading.png" alt="Bounded threading" width="600"></a>
</div>
<div class="title">Figure 13. subscribeOn and dispatchOn/process with an bounded (demand N &lt; Long.MAX) Subscriber</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="streams-microbatching">MicroBatching</h2>
<div class="sectionbody">
<div class="quoteblock">
<blockquote>
Better trade your unused CPU and Memory for your overused Latency
</blockquote>
<div class="attribution">
&#8212; Klingon Proverb
</div>
</div>
<div class="paragraph">
<p>After one or two reads of the <a href="#streams-basics">101 Stream crash intro</a>, you courageous hacker are ready for some <em>quick ROI</em>.
In effect dispatching efficiently is far away from the only item to check in the <strong>way of millions messages per sec todo list</strong>.</p>
</div>
<div class="paragraph">
<p>A common issue in <strong>Distributed Systems</strong> lies in the latency cost over indivudual vs buffered IO writes.
When such situation arises, <strong>MicroBatching</strong> or <em>small chunk-processing</em> is the action to group individual data operations.
Behind the term <code>Micro</code> hides a more concrete behavior named <strong>In Memory</strong>. Since the Speed of Light is still a limitation of systems today, main memory remains cheaper to read than <strong>disk</strong>.</p>
</div>
<div class="exampleblock">
<div class="content">
<div class="paragraph">
<p>Latency Comparison Numbers</p>
</div>
<div class="listingblock">
<div class="content">
<pre>L1 cache reference                            0.5 ns
Branch mispredict                             5   ns
L2 cache reference                            7   ns             14x L1 cache
Mutex lock/unlock                            25   ns
Main memory reference                       100   ns             20x L2 cache, 200x L1 cache
Compress 1K bytes with Zippy              3,000   ns
Send 1K bytes over 1 Gbps network        10,000   ns    0.01 ms
Read 4K randomly from SSD*              150,000   ns    0.15 ms
Read 1 MB sequentially from memory      250,000   ns    0.25 ms
Round trip within same datacenter       500,000   ns    0.5  ms
Read 1 MB sequentially from SSD*      1,000,000   ns    1    ms  4X memory
Disk seek                            10,000,000   ns   10    ms  20x datacenter roundtrip
Read 1 MB sequentially from disk     20,000,000   ns   20    ms  80x memory, 20X SSD
Send packet CA-&gt;Netherlands-&gt;CA     150,000,000   ns  150    ms

Notes
-----
1 ns = 10-9 seconds
1 ms = 10-3 seconds
* Assuming ~1GB/sec SSD

Credit
------
By Jeff Dean:               https://research.google.com/people/jeff/
Originally by Peter Norvig: https://norvig.com/21-days.html#answers</pre>
</div>
</div>
</div>
</div>
<div class="paragraph">
<p><code>Streams</code> are sequences of data, so finding boundaries to cut aggregated buffers is an out-of-the box  API.</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">There are two categories for delimitations:</div>
<div class="ulist">
<ul>
<li>
<p><strong>Buffer</strong> : Concrete boundaries <strong>accumulating</strong> <code>onNext(T)</code> inside grouped <code>List&lt;T&gt;</code> passed to the child <code>Subscriber</code>.</p>
<div class="ulist">
<ul>
<li>
<p>Used best with external API requiring <code>Iterable&lt;T&gt;</code> input argument.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Window</strong> : Discrete boundaries <strong>forwarding</strong> <code>onNext(T)</code> into distinct <code>Stream&lt;T&gt;</code> passed to the child <code>Subscriber</code>.</p>
<div class="ulist">
<ul>
<li>
<p>Used best with accumulators such as <code>reduce</code> or any subscriber/action reacting to <code>onComplete()</code>.</p>
</li>
<li>
<p>Can be combined with <code>flatMap</code> or <code>concatMap</code> which merge back the individual windows in a common <code>Stream&lt;T&gt;</code></p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div>
<div class="sect2">
<h3 id="_into_buffers">Into Buffers</h3>
<div class="paragraph">
<p>Collecting grouped sequences of data <code>T</code> into lists <code>List&lt;T&gt;</code> serves two main purposes:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p>Expose a sequence matching the boundary conditions into an <code>Iterable</code> structure commonly used by JVM APIs</p>
</li>
<li>
<p>Reduce the volume of <code>onNext(T)</code> signals, e.g. <code>buffer(5)</code> will transform a sequence of 10 elements into a sequence of 2 lists (of 5 elements).</p>
</li>
</ul>
</div>
</div>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
Collecting data incurs an overhead in memory and possibly CPU that should be sized appropriately. Small and timed boundaries are advised to avoid any long lasting aggregates.
</td>
</tr>
</table>
</div>
<div class="admonitionblock warning">
<table>
<tr>
<td class="icon">
<i class="fa icon-warning" title="Warning"></i>
</td>
<td class="content">
An <code>Environment</code> must be initialized if the timed <code>buffer()</code> signatures are used without providing the <code>Timer</code> argument.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="type">long</span> timeout = <span class="integer">100</span>;
<span class="directive">final</span> <span class="type">int</span> batchsize = <span class="integer">4</span>;
<span class="predefined-type">CountDownLatch</span> latch = <span class="keyword">new</span> <span class="predefined-type">CountDownLatch</span>(<span class="integer">1</span>);

<span class="directive">final</span> Broadcaster&lt;<span class="predefined-type">Integer</span>&gt; streamBatcher = Broadcaster.&lt;<span class="predefined-type">Integer</span>&gt;create(env);
streamBatcher
  .buffer(batchsize, timeout, <span class="predefined-type">TimeUnit</span>.MILLISECONDS)
  .consume(i -&gt; latch.countDown());


streamBatcher.onNext(<span class="integer">12</span>);
streamBatcher.onNext(<span class="integer">123</span>);
<span class="predefined-type">Thread</span>.sleep(<span class="integer">200</span>);
streamBatcher.onNext(<span class="integer">42</span>);
streamBatcher.onNext(<span class="integer">666</span>);

latch.await(<span class="integer">2</span>, <span class="predefined-type">TimeUnit</span>.SECONDS);</code></pre>
</div>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 10. Chunk processing with Stream buffers (returning Stream&lt;List&lt;T&gt;&gt;):</caption>
<colgroup>
<col style="width: 100%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt; API</p></th>
</tr>
<tr>
<td class="tableblock halign-center valign-middle"><div><div class="paragraph">
<p><strong>Role</strong></p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">buffer(<em>int</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Aggregate until <code>onComplete()</code> or the given <code>int</code> argument is reached which starts over a new aggregation.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">buffer(<strong>Publisher&lt;?&gt;</strong>, <em>Supplier&lt;? extends Publisher&lt;?&gt;&gt;</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Aggregate until <code>onComplete()</code> or when the first <code>Publisher&lt;?&gt;</code> argument emits a signal. The optional <code>Supplier&lt;? extends Publisher&lt;?&gt;&gt;</code> supplies a sequence whose first signal will end the linked aggregation. That means overlapping (sliding buffers) and disjointed aggregation can be emitted to the child <code>Subscriber&lt;List&lt;T&gt;&gt;</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">buffer(<strong>Supplier&lt;? extends Publisher&lt;?&gt;&gt;</strong>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Aggregate until <code>onComplete()</code> or in coordination with a provided <code>Publisher&lt;?&gt;</code>. The <code>Supplier&lt;? extends Publisher&lt;?&gt;&gt;</code> supplies a sequence whose first signal will end the linked aggregation and start a new one immediately.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">buffer(<strong>int, int</strong>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Aggregate until <code>onComplete()</code> or the given <strong>skip</strong> (the second <code>int</code> argument) is reached which starts over a new aggregation. The first <strong>size</strong> <code>int</code> argument will delimit the maximum numger of aggregated elements by buffer. That means overlapping (sliding buffers) and disjointed aggregation can be emitted to the child <code>Subscriber&lt;List&lt;T&gt;&gt;</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">buffer(<strong>long</strong>, TimeUnit, Timer_)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Aggregate until <code>onComplete()</code> or the elapsed <strong>period</strong> (the first <code>long</code> argument) is reached, which starts over a new aggregation.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">buffer(<strong>long, long</strong>, TimeUnit, Timer_)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Aggregate until <code>onComplete()</code> or the given <strong>timeshift</strong> (the second <code>long</code> argument) is reached. The <strong>timespan</strong> (the first <code>long</code> argument) will delimit the maximum numger of aggregated elements by buffer. That means overlapping (sliding buffers) and disjointed aggregation can be emitted to the child <code>Subscriber&lt;List&lt;T&gt;&gt;</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">buffer(<strong>int, long</strong>, <em>TimeUnit, Timer</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">A combination of <code>buffer(int)</code> <strong>OR</strong> <code>buffer(long, TimeUnit, Timer)</code> conditons. It accumulates until the given <strong>size</strong> has been reached or the <strong>timespan</strong> has elapsed.</p></td>
</tr>
</tbody>
</table>
</div>
<div class="sect2">
<h3 id="_into_windows">Into Windows</h3>
<div class="paragraph">
<p>Forwarding grouped sequences of data <code>T</code> into a <code>Stream&lt;T&gt;</code> serves three main purposes:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p>Expose a sequence of data <code>T</code> to various limited grouped observations and accumulation: metrics, average, flexible aggregate (<code>Map</code>, <code>Tuple</code>&#8230;&#8203;).</p>
</li>
<li>
<p>Parallelizing grouped sequences combined with <code>dispatchOn</code> for each generated <code>Stream&lt;T&gt;</code> and merging their results back.</p>
</li>
<li>
<p>Repeat <code>onComplete()</code> for individual grouped sequences, e.g. in <a href="#net-overview">Async IO</a> module to delimit a flush.</p>
</li>
</ul>
</div>
</div>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
<div class="paragraph">
<p><code>Stream&lt;T&gt;</code> windows are slightly less optimized but equivalent aggregating producer than buffer API if combined with the aggregate-all <code>Stream.buffer()</code> method:</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">stream.buffer(<span class="integer">10</span>, <span class="integer">1</span>, <span class="predefined-type">TimeUnit</span>.SECONDS);

<span class="comment">//equivalent to</span>
stream.window(<span class="integer">10</span>, <span class="integer">1</span>, <span class="predefined-type">TimeUnit</span>.SECONDS).flatMap( window -&gt; window.buffer() )</code></pre>
</div>
</div>
</td>
</tr>
</table>
</div>
<div class="admonitionblock warning">
<table>
<tr>
<td class="icon">
<i class="fa icon-warning" title="Warning"></i>
</td>
<td class="content">
An <code>Environment</code> must be initialized if the alias for timed <code>window()</code> are used without providing the <code>Timer</code> argument.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="comment">//create a list of 1000 numbers and prepare a Stream to read it</span>
Stream&lt;<span class="predefined-type">Integer</span>&gt; sensorDataStream = Streams.from(createTestDataset(<span class="integer">1000</span>));

<span class="comment">//wait for all windows of 100 to finish</span>
<span class="predefined-type">CountDownLatch</span> endLatch = <span class="keyword">new</span> <span class="predefined-type">CountDownLatch</span>(<span class="integer">1000</span> / <span class="integer">100</span>);

<span class="predefined-type">Control</span> controls = sensorDataStream
  .window(<span class="integer">100</span>)
  .consume(window -&gt; {
    <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">New window starting</span><span class="delimiter">&quot;</span></span>);
    window
      .reduce(<span class="predefined-type">Integer</span>.MAX_VALUE, (acc, next) -&gt; <span class="predefined-type">Math</span>.min(acc, next))
      .finallyDo(o -&gt; endLatch.countDown())
      .consume(i -&gt; <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">Minimum </span><span class="delimiter">&quot;</span></span> + i));
  });

endLatch.await(<span class="integer">10</span>, <span class="predefined-type">TimeUnit</span>.SECONDS);
<span class="predefined-type">System</span>.out.println(controls.debug());

Assert.assertEquals(<span class="integer">0</span>, endLatch.getCount());</code></pre>
</div>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 11. Chunk processing with Stream (returning Stream&lt;Stream&lt;T&gt;&gt;):</caption>
<colgroup>
<col style="width: 100%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt; API</p></th>
</tr>
<tr>
<td class="tableblock halign-center valign-middle"><div><div class="paragraph">
<p><strong>Role</strong></p>
</div></div></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">window(<em>int</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Forward to a generated <code>Stream&lt;T&gt;</code> until <code>onComplete()</code> or the given <code>int</code> argument is reached which starts over a new <code>Stream</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">window(<strong>Publisher&lt;?&gt;</strong>, <em>Supplier&lt;? extends Publisher&lt;?&gt;&gt;</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Forward to a generated <code>Stream&lt;T&gt;</code> until <code>onComplete()</code> or when the first <code>Publisher&lt;?&gt;</code> argument emits a signal. The optional <code>Supplier&lt;? extends Publisher&lt;?&gt;&gt;</code> supplies a sequence whose first signal will end the linked aggregation. That means overlapping (sliding buffers) and disjointed aggregations can be emitted to the child <code>Subscriber&lt;Stream&lt;T&gt;&gt;</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">window(<strong>Supplier&lt;? extends Publisher&lt;?&gt;&gt;</strong>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Forward to a generated <code>Stream&lt;T&gt;</code>  until <code>onComplete()</code> or in coordination with a provided <code>Publisher&lt;?&gt;</code>. The <code>Supplier&lt;? extends Publisher&lt;?&gt;&gt;</code> supplies a sequence whose first signal will end the linked <code>Stream&lt;T&gt;</code> and start a new one immediately.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">window(<strong>int, int</strong>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Forward to a generated <code>Stream&lt;T&gt;</code>  until <code>onComplete()</code> or the given <strong>skip</strong> (the second <code>int</code> argument) is reached which starts over a new <code>Stream&lt;T&gt;</code>. The <strong>size</strong> (the first <code>int</code> argument) will delimit the maximum numger of aggregated elements by buffer. That means overlapping (sliding buffers) and disjointed sequences can be emitted to the child <code>Subscriber&lt;Stream&lt;T&gt;&gt;</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">window(<strong>long</strong>, TimeUnit, Timer_)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Forward to a generated <code>Stream&lt;T&gt;</code> until <code>onComplete()</code> or the elpased <strong>period</strong> (the <code>long</code> argument) is reached, which starts over a new <code>Stream&lt;T&gt;</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">window(<strong>long, long</strong>, TimeUnit, Timer_)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Forward to a generated <code>Stream&lt;T&gt;</code>  until <code>onComplete()</code> or the given <strong>timeshift</strong> (the second <code>long</code> argument) is reached. The <strong>timespan</strong> (the first <code>long</code> argument) will delimit the maximum numger of aggregated elements by buffer. That means overlapping (sliding buffers) and disjointed sequenced can be emitted to the child <code>Subscriber&lt;Stream&lt;T&gt;&gt;</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">window(<strong>int, long</strong>, <em>TimeUnit, Timer</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">A combination of <code>buffer(int)</code> <strong>OR</strong> <code>buffer(long, TimeUnit, Timer)</code> conditons. It forwards to a generated <code>Stream&lt;T&gt;</code> until the given <strong>size</strong> has been reached or the <strong>timespan</strong> has elapsed.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
<div class="sect1">
<h2 id="streams-backpressure">Backpressure and Overflow</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Backpressure is addressed automatically in many  situations with the <strong>Reactive Streams</strong> contract. If a <code>Subscriber</code> doesn&#8217;t request more than it can actually process (e.g. something other than <code>Long.MAX_VALUE</code>), the upstream source can avoid sending too much data. With a "cold" <code>Publisher</code> this only works when you can stop reading from source at any time: <em>How much to read from a socket, How many rows from a SQL query cursor, how many lines from a File, how many elements from an Iterable</em>&#8230;&#8203;</p>
</div>
<div class="paragraph">
<p>If the source is <strong>hot</strong>, such as a timer or UI events, or the <code>Subscriber</code> might request <code>Long.MAX_VALUE</code> on a large dataset, a strategy must be explicitely picked by the developer to deal with <strong>backpressure</strong>.</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">Reactor provides a set of APIs to deal with Hot and Cold sequences:</div>
<div class="ulist">
<ul>
<li>
<p>Uncontrolled sequences (Hot) should be actively managed</p>
<div class="ulist">
<ul>
<li>
<p>By <strong>reducing</strong> the sequence volume, e.g. "sampling"</p>
</li>
<li>
<p>By <strong>ignoring</strong> data when the demand exceeds capacity</p>
</li>
<li>
<p>By <strong>buffering</strong> data when the demand exceeds capacity</p>
</li>
</ul>
</div>
</li>
<li>
<p>Controlled sequences (Cold) should be passively managed</p>
<div class="ulist">
<ul>
<li>
<p>By <strong>lowering demand</strong> from the <code>Subscriber</code> or at any point of the <code>Stream</code></p>
</li>
<li>
<p>By <strong>gapping demand</strong> with delayed requests</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div>
<div class="paragraph">
<p>A common example used extensively in the <strong>Reactive Extensions</strong> documentation is the <strong>Marble Diagram</strong>. The dual timeline helps visualize when and what is observed in the <code>Publisher</code> or <code>Stream</code> and in a <code>Subscriber</code> (e.g. an <code>Action</code>). We will use these diagrams here to emphasize the demand flow, where usually such a diagram details the nature of the transformation like <em>map</em> or <em>filter</em>.</p>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/marble/marble-101.png"><img src="images/marble/marble-101.png" alt="Marble Diagrams" width="650"></a>
</div>
</div>
<div class="paragraph">
<p><strong>Reactor</strong> will automatically provide for an in-memory overflow buffer when the dispatcher or the capacity differs from one action to another. This will not apply to <code>Core Processors</code>, which handle the overflow in their own way. Dispatchers can be re-used and <strong>Reactor</strong> must limit the number of dispatches where it can, hence the in-memory buffer added by <code>Action</code> when dispatchers differ.</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Streams.just(<span class="integer">1</span>,<span class="integer">2</span>,<span class="integer">3</span>,<span class="integer">4</span>,<span class="integer">5</span>)
  .buffer(<span class="integer">3</span>) <i class="conum" data-value="1"></i><b>(1)</b>
  <span class="comment">//onOverflowBuffer()</span>
  .capacity(<span class="integer">2</span>) <i class="conum" data-value="2"></i><b>(2)</b>
  .consume()


Streams.just(<span class="integer">1</span>,<span class="integer">2</span>,<span class="integer">3</span>,<span class="integer">4</span>,<span class="integer">5</span>)
  .dispatchOn(dispatcher1) <i class="conum" data-value="3"></i><b>(3)</b>
  <span class="comment">//onOverflowBuffer()</span>
  .dispatchOn(dispatcher2) <i class="conum" data-value="4"></i><b>(4)</b>
  .consume()</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>The buffer operation set capacity(3)</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>consume() or any downstream action is set with capacity(2), an implicit onOverflowBuffer() is added</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>A first action running on dispatcher1</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>A second action running on a different dispatcher2, an implicit onOverflowBuffer() is added</td>
</tr>
</table>
</div>
<div class="paragraph">
<p>Ultimately the <code>Subscriber</code> can request data one by one, limiting the in-flight data to one element all along the pipeline and requesting one more after each successful <code>onNext(T)</code>. The same behavior can be obtained with <code>capacity(1).consume(...)</code>.</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Streams.range(<span class="integer">1</span>,<span class="integer">1000000</span>)
  .subscribe(<span class="keyword">new</span> DefaultSubscriber&lt;<span class="predefined-type">Long</span>&gt;(){ <i class="conum" data-value="1"></i><b>(1)</b>
    Subscription sub;

    <span class="annotation">@Override</span>
    <span class="type">void</span> onSubscribe(Subscription sub){
      <span class="local-variable">this</span>.sub = sub;
      sub.request(<span class="integer">1</span>); <i class="conum" data-value="2"></i><b>(2)</b>
    }

    <span class="annotation">@Override</span>
    <span class="type">void</span> onNext(<span class="predefined-type">Long</span> n){
      httpClient.get(<span class="string"><span class="delimiter">&quot;</span><span class="content">localhost/</span><span class="delimiter">&quot;</span></span>+n).onSuccess(rep -&gt; sub.request(<span class="integer">1</span>)); <i class="conum" data-value="3"></i><b>(3)</b>
    }
  );</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Use a <code>DefaultSubscriber</code> to avoid implementing all <code>Subscriber</code> methods.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Schedule a first demand request after keeping a reference to the subscription.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Use <a href="#net-http101">Async HTTP API</a> to request more only on successful GET. That will naturally propagate the latency information back to the <code>RangeStream</code> <code>Publisher</code>. One can imagine then measuring the time difference between two requests and how that gives an interesting insight into the processing and IO latency.</td>
</tr>
</table>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 12. Controlling the volume of in-flight data</caption>
<colgroup>
<col style="width: 100%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt;</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">subscribe(<strong>Subscriber&lt;T&gt;</strong>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">A custom <code>Subscriber&lt;T&gt;</code> will have the flexibility to request whenever it wishes. It&#8217;s best to change the size these requests if the <code>Subscriber</code> uses blocking operations.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">capacity(<strong>long</strong>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock"><a href="#stream-capacity">Set the capacity</a> to this <code>Stream&lt;T&gt;</code> and all downstream actions.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">onOverflowBuffer(<em>CompletableQueue</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-center valign-middle"><div><div class="paragraph">
<p>Create or use the given <code>CompletableQueue</code> to store the overflow elements. Overflow occurs when a <code>Publisher</code> sends more data than a <code>Subscriber</code> has actually requested. Overflow will be drained over the next calls to <code>request(long)</code>.</p>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/marble/marble-overflowbuffer.png"><img src="images/marble/marble-overflowbuffer.png" alt="onOverflowBuffer()" width="500"></a>
</div>
</div></div></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">onOverflowDrop()</p></th>
</tr>
<tr>
<td class="tableblock halign-center valign-middle"><div><div class="paragraph">
<p>Ignore the overflowed elements. Overflow occurs when a <code>Publisher</code> sends more data than a <code>Subscriber</code> has actually requested. Overflow will be drained over the next calls to <code>request(long)</code>.</p>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/marble/marble-overflowdrop.png"><img src="images/marble/marble-overflowdrop.png" alt="onOverflowDrop()" width="500"></a>
</div>
</div></div></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">throttle(<strong>long</strong>)</p></th>
</tr>
<tr>
<td class="tableblock halign-center valign-middle"><div><div class="paragraph">
<p>Delay downstream <code>request(long)</code> and periodically decrement the accumulated demand one by one to request upstream.</p>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/marble/marble-throttle.png"><img src="images/marble/marble-throttle.png" alt="throttle(delay)" width="500"></a>
</div>
</div></div></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">requestWhen(<strong>Function&lt;Stream&lt;Long&gt;, Publisher&lt;Long&gt;&gt;</strong>)</p></th>
</tr>
<tr>
<td class="tableblock halign-center valign-middle"><div><div class="paragraph">
<p>Pass any downstream <code>request(long)</code> to <code>Stream&lt;Long&gt;</code> sequence of requests that can be altered and returned using any form of <code>Publisher&lt;Long&gt;</code>. The <code>RequestWhenAction</code> will subscribe to the produced sequence and immiately forward <code>onNext(Long)</code> to the upstream <code>request(long)</code>. It behaves similarly to <code>adaptiveConsume</code> but can be inserted at any point in the <code>Stream</code> pipeline.</p>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/marble/marble-requestwhen.png"><img src="images/marble/marble-requestwhen.png" alt="requestWhen(requestMapper)" width="500"></a>
</div>
</div></div></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">batchConsume(<strong>Consumer&lt;T&gt;</strong>, <em>Consumer&lt;T&gt;, Consumer&lt;T&gt;</em>, <strong>Function&lt;Long,Long&gt;</strong>)
</p><p class="tableblock"><em>batchConsumeOn</em></p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Similar to <code>consume</code> but will request the mapped <code>Long</code> demand given the previous demand and starting with the default <code>Stream.capacity()</code>. Useful for adapting the demand from various factors.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">adaptiveConsume(<strong>Consumer&lt;T&gt;</strong>, <em>Consumer&lt;T&gt;, Consumer&lt;T&gt;</em>, <strong>Function&lt;Stream&lt;Long&gt;,Publisher&lt;Long&gt;&gt;</strong>),
</p><p class="tableblock"><em>adaptiveConsumeOn</em></p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Similar to <code>batchConsume</code> but will request the computed sequence of demand <code>Long</code>. It can be used to insert flow-control such as <code>Streams.timer()</code> to delay demand.  The <code>AdaptiveConsumerAction</code> will subscribe to the produced sequence and immediately forwards <code>onNext(Long)</code> to the upstream <code>request(long)</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">process(<strong>Processor&lt;T, ?&gt;</strong>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Any <code>Processor</code> can also take care of transforming the demand or buffer. It is worth checking into the behavior of the specific <code>Processor</code> implementation in use.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock"><em>All</em> filter(<em>arguments</em>), take(<em>arguments</em>), takeWhile(<em>arguments</em>)&#8230;&#8203;</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">All limit operations can be used to proactively limit the volume of a <code>Stream</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">buffer(<em>arguments</em>), reduce(<em>arguments</em>), count(<em>arguments</em>)&#8230;&#8203;</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">All aggregating and metrics operations can be used to proactively limit the volume of a <code>Stream</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock"><em>All</em> sample(<em>arguments</em>), sampleFirst(<em>arguments</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Reduce the volume of a <code>Stream&lt;T&gt;</code> by selecting the last (or the first) <code>onNext(T)</code> signals matching the given conditions. These conditions can be timed, sized, timed or sized, and interactive (event-driven).</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">zip(<em>arguments</em>), zipWith(<em>arguments</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Reduce the volume of N <code>Stream&lt;T&gt;</code> to the least signals producing zipped <code>Publisher</code>. The aggregated signals from each <code>Publisher</code> can be used to produce a distinct value from the N most recent upstream <code>onNext(T)</code>.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="sect1">
<h2 id="streams-combine">Combinatory Operations</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Combining <code>Publishers</code> allows for coordination between multiple <strong>concurrent sequences</strong> of data.
They also serve the purpose of <a href="#stream-flatmap">asynchronous transformations</a>, with the resulting sequences being merged.</p>
</div>
<div class="paragraph">
<p>Coordinating in a non-blocking way will free the developer from using <code>Future.get()</code> or <code>Promise.await()</code>, a perilous task when it comes to more than one signal. Being non-blocking means that distinct pipelines won&#8217;t wait on anything other than <code>Subscriber</code> demand. The <code>Subscriber</code> requests will be split, with a minimum request of one for each merged <code>Publisher</code>.</p>
</div>
<div class="paragraph">
<p>Merging actions are modeled in <code>FanInAction</code> and take care of concurrent signaling with a <strong>thread-stealing</strong> <code>SerializedSubscriber</code> proxy to the delegate <code>Subscriber</code>. For each signal it will verify if the correct thread is already running the delegate <code>Subscriber</code> and rescheduling the signal if not. The signal will then be polled when the busy thread exits <code>Subscriber</code> code, possibly running the signal in a different thread than originally produced on.</p>
</div>
<div class="admonitionblock warning">
<table>
<tr>
<td class="icon">
<i class="fa icon-warning" title="Warning"></i>
</td>
<td class="content">
<a href="#streams-backpressure">Reducing the demand volume</a> before using <code>flatMap</code> might be a good or a bad idea. In effect it doesn&#8217;t deserve the merging action to subscribe to many parallel <code>Publisher</code> if it can&#8217;t actually process them all. However it limiting the parallel <code>Publisher</code> size might also not give a chance to faster <code>Publisher</code> pending a request to be delivered.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Stream.zipWith(Function)</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Streams
  .range(<span class="integer">1</span>, <span class="integer">100</span>)
  .zipWith( Streams.generate(<span class="predefined-type">System</span>::currentTimeMillis), tuple -&gt; tuple ) <i class="conum" data-value="1"></i><b>(1)</b>
  .consume(
    tuple -&gt; <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">number: </span><span class="delimiter">&quot;</span></span>+tuple.getT1()+<span class="string"><span class="delimiter">&quot;</span><span class="content"> time: </span><span class="delimiter">&quot;</span></span>+tuple.getT2()) , <i class="conum" data-value="2"></i><b>(2)</b>
    <span class="predefined-type">Throwable</span>::printStackTrace,
    avoid -&gt; <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">--complete--</span><span class="delimiter">&quot;</span></span>)
  );</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>"Zip" or aggregate the most recent signal from <code>RangeStream</code> and the passed <code>SupplierStream</code> providing current time</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>"Zip" produces tuples of data from each zipped <code>Publisher</code> in the declarative order (left to right, <em>stream1.zipWith(stream2)</em>).</td>
</tr>
</table>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 13. Combining Data Sources</caption>
<colgroup>
<col style="width: 100%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Functional API or Factory method</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.flatMap(Function&lt;T, Publisher&lt;V&gt;&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">An <a href="#stream-flatmap">Async transformation</a> is a typed shortcut for <code>map(Function&lt;T, Publisher&lt;V&gt;&gt;).merge()</code>.
</p><p class="tableblock">The mapping part produces a <code>Publisher&lt;V&gt;</code> eventully using the passed data <code>T</code>, a common pattern used in <a href="#streams-microservice">MicroService architecture</a>.
</p><p class="tableblock">The merging part transforms the sequence of produced <code>Publisher&lt;V&gt;</code> into a sequence of <code>V</code> by <em>safely</em> subscribing in parallel to all of them. There is no ordering guaranteed, it is <strong>interleaved</strong> sequence of <code>V</code>. All merged <code>Publisher&lt;T&gt;</code> must complete before the <code>Subscriber&lt;T&gt;</code> can complete.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.switchOnNext(Publisher&lt;Publisher&lt;T&gt;&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">A Stream alterning in FIFO order between emitted <code>onNext(Publisher&lt;T&gt;)</code> from the passed Publisher. The signals will result in downstream Subscriber&lt;T&gt; receiving the next Publisher sequence of <code>onNext(T)</code>.
It might interrupt a current upstream emission when the <code>onNext(Publisher&lt;T&gt;)</code> signal is received.
All merged <code>Publisher&lt;T&gt;</code> must complete before the <code>Subscriber&lt;T&gt;</code> can complete.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.merge(Publisher&lt;T&gt;, <em>Publisher&lt;T&gt; x7</em>)
</p><p class="tableblock">Streams.merge(Publisher&lt;Publisher&lt;T&gt;&gt;)
</p><p class="tableblock">Stream.mergeWith(Publisher&lt;T&gt;)
</p><p class="tableblock">Stream.merge()</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Transform upstream sequence of <code>Publisher&lt;T&gt;</code> into a sequence of <code>T</code> by <em>safely</em> subscribing in parallel to all of them. There is no ordering guaranteed, it is <strong>interleaved</strong> sequence of <code>T</code>. If the arguments are directly <code>Publisher&lt;T&gt;</code> like in <code>Stream.mergeWith(Publisher&lt;T&gt;)</code> or <code>Streams.merge(Publisher&lt;T&gt;, Publisher&lt;T&gt;)</code>, the <code>MergeAction</code> will subscribe to them directly and size more efficiently (known number of parallel upstreams). All merged <code>Publisher&lt;T&gt;</code> must complete before the <code>Subscriber&lt;T&gt;</code> can complete.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.concat(Publisher&lt;T&gt;, <em>Publisher&lt;T&gt; x7</em>)
</p><p class="tableblock">Streams.concat(Publisher&lt;Publisher&lt;T&gt;&gt;)
</p><p class="tableblock">Stream.concatWith(Publisher)
</p><p class="tableblock">Stream.startWith(Publisher)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Similar to <code>merge()</code> actions but if a Publisher&lt;T&gt; is already emitting, wait for it to <code>onComplete()</code> before draining the next pending Publisher&lt;T&gt;. The sequences will be subscribed in declarative order, from left to right, e.g. <code>stream1.concatWith(stream2)</code> or with the argument given in <code>stream2.startWith(stream1)</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.combineLatest(Publisher&lt;T&gt;, <em>Publisher&lt;T&gt; x7</em>, Function&lt;Tuple,V&gt;)
</p><p class="tableblock">Streams.combineLatest(Publisher&lt;Publisher&lt;T&gt;&gt;, Function&lt;Tuple,V&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Combine the most recent <code>onNext(T)</code> signal from each distinct <code>Publisher&lt;T&gt;</code>. Each signal combines until a future <code>onNext(T)</code> from its source <code>Publisher&lt;T&gt;</code> replaces it. <strong>After</strong> all <code>Publisher&lt;T&gt;</code> have emitted at least one signal, the given combinator function will accept all recent signals and produce the desired combined object. If any <code>Publisher&lt;T&gt;</code> completes, the downstream <code>Subscriber&lt;T&gt;</code> will complete.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.zip(Publisher&lt;T&gt;, <em>Publisher&lt;T&gt; x7</em>, Function&lt;Tuple,V&gt;)
</p><p class="tableblock">Streams.zip(Publisher&lt;Publisher&lt;T&gt;&gt;, Function&lt;Tuple,V&gt;)
</p><p class="tableblock">Stream.zipWith(Publisher&lt;T&gt;, Function&lt;Tuple2,V&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Combine the most recent <code>onNext(T)</code> signal from each distinct <code>Publisher&lt;T&gt;</code>. Each signal combines only once. <strong>Everytime</strong> all <code>Publisher&lt;T&gt;</code> have emitted one signal, the given zipper function will receive them and produce the desired zipped object. If any <code>Publisher&lt;T&gt;</code> completes, the downstream <code>Subscriber&lt;T&gt;</code> will complete.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.join(Publisher&lt;T&gt;, <em>Publisher&lt;T&gt; x7</em>)
</p><p class="tableblock">Streams.join(Publisher&lt;Publisher&lt;T&gt;&gt;)
</p><p class="tableblock">Stream.joinWith(Publisher&lt;T&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">A shortcut for <code>zip</code> with a predefined zipper function transforming each most recent <code>Tuple</code> into a <code>List&lt;?&gt;</code>.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="sect1">
<h2 id="streams-microservice">MicroServices</h2>
<div class="sectionbody">
<div class="paragraph">
<p>The notion of <a href="https://martinfowler.com/articles/microservices.html">MicroService</a> has been an increasingly popular term over the last years. Simply put, we code software components with a focused purpose to encourage <em>isolation</em>, <em>adapted scaling</em> and <em>reuse</em>. In fact it has been over 30 years we use them:</p>
</div>
<div class="listingblock">
<div class="title">An example of microservices in Unix</div>
<div class="content">
<pre>history | grep password</pre>
</div>
</div>
<div class="paragraph">
<p>Even within the boundaries of the application, we can find the similar concept of functional granularity:</p>
</div>
<div class="listingblock">
<div class="title">An example of microservices in <em>imperative</em> Java code</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">User rick = userService.get(<span class="string"><span class="delimiter">&quot;</span><span class="content">Rick</span><span class="delimiter">&quot;</span></span>);
User morty = userService.get(<span class="string"><span class="delimiter">&quot;</span><span class="content">Morty</span><span class="delimiter">&quot;</span></span>);
<span class="predefined-type">List</span>&lt;Mission&gt; assigned = missionService.findAllByUserAndUser(rick, morty);</code></pre>
</div>
</div>
<div class="paragraph">
<p>Of course the application has been widely popular within distributed systems and <a href="https://12factor.net">cloud-ready architectures</a>. When the function is isolated enough, it will depend on N other ones for : Data access, subroutine calls over network, posting into message bus, querying an HTTP REST endpoint etc. This is where troubles begin: <strong>the execution flow is crossing multiple context boundaries</strong>. Relatively latency and failure will start to scale up as the system grows in volume and access.</p>
</div>
<div class="paragraph">
<p>At this point we can decide to <em>scale-out</em>, after all platforms such as <a href="https://www.cloudfoundry.org">CloudFoundry</a> allow for elastic scaling of JVM apps and beyond. But looking at our CPU and memory use, it didn&#8217;t seem particularly under pressure. Of course it was not, each remote call was just blocking the whole service and preventing concurrent user requests to kick in: They are just parked in some thread pool queue. In the meantime the active request was happily seating for a few milliseconds or more waiting for a remote HTTP call socket to actually write, a delay we call <strong>latency</strong> here.</p>
</div>
<div class="paragraph">
<p>The same applies to errors, we can make applications more resilient (fallbacks, timeouts, retries&#8230;&#8203;) individually first and not rely on <em>scaling out</em>. The classic hope is that a replicate microservice will pick up the requests when a load-balancer will detect the failure:</p>
</div>
<div class="listingblock">
<div class="content">
<pre>Load Balancer: "are you dead ?"
30 sec later
Load Balancer: "are you dead ?"
30 sec later
Load Balancer: "you're dead !"
MicroService "I'am alive !"</pre>
</div>
</div>
<h4 id="_in_a_distributed_system_coordination_pulls_a_very_long_string_of_issues_you_wish_you_have_never_faced" class="discrete">In a Distributed System, coordination pulls a very long string of issues you wish you have never faced.</h4>
<div class="paragraph">
<p>A <code>Publisher</code> like a <code>Stream</code> or a <code>Promise</code> is ideal to confront <strong>MicroServices</strong> latency and errors. To improve the situation with better error isolation and non-blocking service calls, code has to be designed with these two constraints in mind. To put on your side the best chances for a successful migration story to a Reactive Architecture, you might prefer to work step by step with quick wins and a few adjustements, test and iterate to the next step.</p>
</div>
<div class="paragraph">
<p>In this section we&#8217;re going to cover the basics to create a reactive facade gating each costly remote call, build functional services and make them latency-ready.</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="title">Becoming Reactive with Reactor in 3 steps:</div>
<div class="olist arabic">
<ol class="arabic">
<li>
<p>Transform target service calls into <em>unbounded</em> <code>Stream</code> or <code>Promise</code> return types</p>
<div class="ulist">
<ul>
<li>
<p>Asynchronous switch for Blocking &#8594; Non Blocking conversion</p>
</li>
<li>
<p>Error isolation</p>
</li>
</ul>
</div>
</li>
<li>
<p>Compose services with the <strong>Reactor Stream</strong> API</p>
<div class="ulist">
<ul>
<li>
<p>Blocking &#8594; Non Blocking coordination</p>
</li>
<li>
<p>Parallelize Blocking calls</p>
</li>
</ul>
</div>
</li>
<li>
<p>Evolve transformed services to backpressure ready <code>Stream</code></p>
<div class="ulist">
<ul>
<li>
<p>Chunk processing/reading with bounded access</p>
</li>
<li>
<p>Optimize IO operations with Microbatching</p>
</li>
</ul>
</div>
</li>
</ol>
</div>
</div>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 14. Common Actions at play when reading remote resources</caption>
<colgroup>
<col style="width: 100%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Functional API or Factory method</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Streams.create(Publisher), Streams.defer(Supplier), Streams.wrap(Publisher), Streams.generate(Supplier)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Protecting resource access with a <code>Publisher</code> is encouraged. A few <a href="#streams-basics">Stream factories</a> will be particularly useful. The point of creating a <code>Publisher</code> is to only <code>onNext(T)</code> when the data is ready such as in an IO callback. The read should be triggered by a <code>Subscriber</code> request if possible to implement a form of backpressure.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.timeout(<em>arguments</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Accessing an external resource, especially remote, should always be limited in time to become more resilient to external conditions such as network partitions. Timeout operations can fallback to another <code>Publisher</code> for alternative  service call or just <code>onError(TimeoutException)</code>. The timer resets each time a fresh <code>onNext(T)</code> is observed.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.take(<em>arguments</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Similar to <code>timeout()</code>, a need to scope in size an external resource is a common one. It&#8217;s also useful to fully trigger a pipeline including <code>onComplete()</code> processing.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.flatMap(Function&lt;T,Publisher&lt;V&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">An <a href="#stream-flatmap">Async transformation</a> that produces a <code>Publisher&lt;V&gt;</code> eventully using the passed data <code>T</code>, the ideal place to hook in a call to another service before resuming the current processing.
</p><p class="tableblock">The sequence of produced <code>Publisher&lt;V&gt;</code> will flow in the <code>Subscriber</code> into a sequence of <code>V</code> by <em>safely</em> subscribing in parallel.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.subscribeOn(Dispatcher), Stream.dispatchOn(Dispatcher), <em>Core Processors</em></p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><div><div class="paragraph">
<p><a href="#streams-multithreading">Threading control</a> is strategic:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p>Slow MicroService, low volume or low throughput, e.g. HTTP GET &#8594; <code>subscribeOn(workQueueDispatcher())</code> to scale-up concurrent service calls.</p>
</li>
<li>
<p>Fast MicroService, high volume or high throughput, e.g. Message Bus &#8594; <code>dispatchOn(sharedDispatcher())</code> or <code>RingBufferXXXProcessor.create()</code> to scale up message-dispatching.</p>
</li>
</ul>
</div>
</div>
</div></div></td>
</tr>
</tbody>
</table>
<div class="sect2">
<h3 id="streams-microservice-start">Creating Non-Blocking Services</h3>
<div class="paragraph">
<p>The first step is to isolate the microservice access. Instead of returning a type <code>T</code> or <code>Future&lt;T&gt;</code>, we will now start using <code>Publisher&lt;T&gt;</code> and specifically <code>Stream&lt;T&gt;</code> or <code>Promise&lt;T&gt;</code>. The immediate benefit is we don&#8217;t need to worry anymore about error handling and threading (yet): Errors are propagated in <code>onError</code> calls (no bubble up), threading might be tuned later for instance using <code>dispatchOn</code>. The additional bonus is we get to make our code more <em>functional</em>. It also works nice with Java 8 Lambdas! The target will be to reduce control brackets noise (if, for, while&#8230;&#8203;) and limit more the need for sharing context. Ultimately our target design will encourage streaming over polling large datasets : functions will apply to a sequence, result by result, avoiding loop duplication.</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
We prefer to use the implementation artefacts and not <code>Publisher&lt;T&gt;</code> to get compile-time access to all the <strong>Reactor Stream</strong> API, unless we want to be API agnostic (a possible case for library developers). <code>Streams.wrap(Publisher&lt;T&gt;)</code> will do the trick anyway to convert such generic return type into a proper <code>Stream&lt;T&gt;</code>.
</td>
</tr>
</table>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 15. Evolving to reactive microservices, part 1, error isolation and non-blocking in some UserService</caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-center valign-middle"><p class="tableblock">The Not So Much Win</p></th>
<th class="tableblock halign-center valign-middle"><p class="tableblock">The Win</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><div><div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="directive">public</span> User get(<span class="predefined-type">String</span> name)
<span class="directive">throws</span> <span class="exception">Exception</span> {
  <span class="predefined-type">Result</span> r = userDB.findByName(name);
  <span class="keyword">return</span> convert(r);
}

<span class="directive">public</span> <span class="predefined-type">List</span>&lt;User&gt; allFriends(User user)
<span class="directive">throws</span> <span class="exception">Exception</span> {
  <span class="predefined-type">ResultSet</span> rs = userDB.findAllFriends(user);
  <span class="keyword">return</span> convertToList(r);
}

<span class="directive">public</span> <span class="predefined-type">Future</span>&lt;<span class="predefined-type">List</span>&lt;User&gt;&gt; filteredFind(<span class="predefined-type">String</span> name)
<span class="directive">throws</span> <span class="exception">Exception</span> {
  User user = get(name);
  <span class="keyword">if</span>(user == <span class="predefined-constant">null</span> || !user.isAdmin()){
    <span class="keyword">return</span> CompletedFuture.completedFuture(<span class="predefined-constant">null</span>);
  } <span class="keyword">else</span> {
    <span class="comment">//could be in an async thread if wanted</span>
    <span class="keyword">return</span> CompletedFuture.completedFuture(allFriends(user));
  }
}</code></pre>
</div>
</div></div></td>
<td class="tableblock halign-left valign-top"><div><div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="directive">public</span> Promise&lt;User&gt; get(<span class="directive">final</span> <span class="predefined-type">String</span> name) {
  <span class="keyword">return</span> Promises
    .task( () -&gt; userDB.findByName(name))
    .timeout(<span class="integer">3</span>, <span class="predefined-type">TimeUnit</span>.Seconds)
    .map(<span class="local-variable">this</span>::convert)
    .subscribeOn(workDispatcher());
}

<span class="directive">public</span> Stream&lt;User&gt; allFriends(<span class="directive">final</span> User user)  {
  <span class="keyword">return</span> Streams
    .defer(() -&gt;
      Streams.just(userDB.findAllFriends(user)))
    .timeout(<span class="integer">3</span>, <span class="predefined-type">TimeUnit</span>.Seconds)
    .map(<span class="local-variable">this</span>::convertToList)
    .flatMap(Streams::from)
    .dispatchOn(cachedDispatcher());
    .subscribeOn(workDispatcher());
}

<span class="directive">public</span> Stream&lt;User&gt; filteredFind(<span class="predefined-type">String</span> name){
    <span class="keyword">return</span> get(name)
      .stream()
      .filter(User::isAdmin)
      .flatMap(<span class="local-variable">this</span>::allFriends);
}</code></pre>
</div>
</div></div></td>
</tr>
<tr>
<th class="tableblock halign-center valign-middle" colspan="2"><p class="tableblock">The Result</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><div><div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p>In <strong>all query methods</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>No more <strong>throws Exception</strong>, its all passed in the pipeline</p>
</li>
<li>
<p>No more control logic, we use predefined operators such as map or filter</p>
</li>
<li>
<p>Only return <code>Publisher</code> (Stream or Promise)</p>
</li>
<li>
<p>Limit blocking queries in time with timeout (can be used later for retrying, fallback etc)</p>
</li>
<li>
<p>Use a pooled workDispatcher thread On Subscribe</p>
</li>
</ul>
</div>
</li>
<li>
<p>In <strong>get(name)</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>Use of typed <strong>single data</strong> Publisher, or <code>Promise</code>.</p>
</li>
<li>
<p>On Subscribe, call the <strong>task</strong> callback</p>
</li>
</ul>
</div>
</li>
<li>
<p>In <strong>allFriends(user)</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>Use <code>defer()</code> to invoke the DB query on the <strong>onSubscribe</strong> thread, lazily</p>
</li>
<li>
<p>No backpressure strategy yet and we read all the results in one blocking (but async) call</p>
</li>
<li>
<p>We convert returned list into a data stream in FlatMap</p>
</li>
<li>
<p>Dispatch each signal on an async dispatcher so downstream processing doesn&#8217;t negatively impact the read</p>
</li>
</ul>
</div>
</li>
<li>
<p>In <strong>filteredFind(name)</strong>:</p>
<div class="ulist">
<ul>
<li>
<p>We convert a <code>Promise</code> from first get to a Stream with <code>stream()</code></p>
</li>
<li>
<p>We only call allFriends() sub-stream if there is a valid user</p>
</li>
<li>
<p>The returned Stream&lt;User&gt; resume on the first allFriend() signal</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div></div></td>
</tr>
</tbody>
</table>
</div>
<div class="sect2">
<h3 id="streams-microservice-compose">Composing multiple Services Calls</h3>
<div class="paragraph">
<p>In this second step, we will expand our thinking to the consuming aspect. In a transition phase, keep in mind that <code>Stream</code> can be <a href="#streams-blocking">blocked using operators</a>.</p>
</div>
<div class="paragraph">
<p>There are two issues to address in target: robustness (network partition tolerance etc) and avoiding to wait for a service before processing another:</p>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 16. Evolving to reactive microservices, part 2, parallel requests and resiliency in some RickAndMortyService</caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-center valign-middle"><p class="tableblock">The Not So Much Win</p></th>
<th class="tableblock halign-center valign-middle"><p class="tableblock">The Win</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><div><div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="type">int</span> tries = <span class="integer">0</span>;
<span class="keyword">while</span>(tries &lt; <span class="integer">3</span>){
  <span class="keyword">try</span>{
    <span class="predefined-type">Future</span>&lt;<span class="predefined-type">List</span>&lt;User&gt;&gt; rickFriends =
      userService.fitleredFind(<span class="string"><span class="delimiter">&quot;</span><span class="content">Rick</span><span class="delimiter">&quot;</span></span>);

    <span class="predefined-type">Future</span>&lt;<span class="predefined-type">List</span>&lt;User&gt;&gt; mortyFriends =
      userService.fitleredFind(<span class="string"><span class="delimiter">&quot;</span><span class="content">Morty</span><span class="delimiter">&quot;</span></span>);

    <span class="predefined-type">System</span>.out.println(
      rickFriends.get(<span class="integer">3</span>, <span class="predefined-type">TimeUnit</span>.SECONDS)
      .addAll(
        mortyFriends.get(<span class="integer">3</span>, <span class="predefined-type">TimeUnit</span>.SECONDS))
    );

  }<span class="keyword">catch</span>(<span class="exception">Exception</span> e){
    <span class="keyword">if</span>(tries++ &gt;= <span class="integer">3</span>) <span class="keyword">throw</span> e;
    <span class="predefined-type">Thread</span>.sleep(tries*<span class="integer">1000</span>);
  }
}</code></pre>
</div>
</div></div></td>
<td class="tableblock halign-left valign-top"><div><div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="keyword">return</span> Streams.merge(
  userService.filteredFind(<span class="string"><span class="delimiter">&quot;</span><span class="content">Rick</span><span class="delimiter">&quot;</span></span>),
  userService.filteredFind(<span class="string"><span class="delimiter">&quot;</span><span class="content">Morty</span><span class="delimiter">&quot;</span></span>)
)
.buffer()
.retryWhen( errors -&gt;
  errors
  .zipWith(Streams.range(<span class="integer">1</span>,<span class="integer">3</span>), t -&gt; t.getT2())
  .flatMap( tries -&gt; Streams.timer(tries) )
)
.consume(<span class="predefined-type">System</span>.out::println);</code></pre>
</div>
</div></div></td>
</tr>
<tr>
<th class="tableblock halign-center valign-middle" colspan="2"><p class="tableblock">The Result</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><div><div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p><code>Streams.merge()</code> is a non-blocking coordinating operation mixing the two queries in one</p>
</li>
<li>
<p><code>buffer()</code> will aggregate all results until completion or error (which we timed previously)</p>
</li>
<li>
<p><code>retryWhen(Function&lt;Stream&lt;Throwable&gt;, Publisher&lt;?&gt;&gt;</code> will keep re-subscribing if an error is propagated</p>
<div class="ulist">
<ul>
<li>
<p><code>zipWith</code> will combine errors with a number of tries up to 3 times</p>
</li>
<li>
<p><code>zipWith</code> only return the number of tries from the tuple</p>
</li>
<li>
<p><code>flatMap</code> + <code>Streams.timer(long)</code> convert each try into a delayed signal (seconds by default)</p>
</li>
<li>
<p>Each time a signal is sent by this returned <code>Publisher</code>, cancel and subscribe again, until a <code>onComplete</code> or <code>onError</code> is sent.</p>
</li>
<li>
<p><code>flatMap</code> only completes if the internal timer AND the upstream have completed, so after the range of 3 or after errors sequence itself terminates.</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div></div></td>
</tr>
</tbody>
</table>
</div>
<div class="sect2">
<h3 id="streams-microservice-backpressure">Supporting Reactive Backpressure</h3>
<div class="paragraph">
<p>In this last step, we pay a visit to the <em>UserService.allFriends</em> query which is right now polling entire datasets from Database.</p>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 17. Evolving to reactive microservices, part 3, backpressure in UserService.allFriends</caption>
<colgroup>
<col style="width: 50%;">
<col style="width: 50%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-center valign-middle"><p class="tableblock">The Win</p></th>
<th class="tableblock halign-center valign-middle"><p class="tableblock">The Epic Win</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><div><div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="keyword">return</span> Streams
  .defer(() -&gt;
    Streams.just(userDB.findAllFriends(user)))
  .timeout(<span class="integer">3</span>, <span class="predefined-type">TimeUnit</span>.Seconds)
  .map(<span class="local-variable">this</span>::convertToList)
  .flatMap(Streams::from)
  .dispatchOn(cachedDispatcher());
  .subscribeOn(workDispatcher());

stream
  .buffer()
  .consume(<span class="predefined-type">System</span>.out::println);</code></pre>
</div>
</div></div></td>
<td class="tableblock halign-left valign-top"><div><div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="keyword">return</span> Streams
  .createWith(
    (demand, sub) -&gt; {
      <span class="predefined-type">ResultSet</span> rs = sub.context();
      <span class="type">long</span> cursor = <span class="integer">0l</span>;

      <span class="keyword">while</span>(rs.hasNext()
        &amp;&amp; cursor++ &lt; demand
        &amp;&amp; !sub.isCancelled()){

        sub.onNext(rs.next());
      }

      <span class="keyword">if</span>(!rs.hasNext()){
        sub.onComplete();
      }
    },
    sub -&gt; userDB.findAllFriends(user),
    resultSet -&gt; resultSet.close()
  )
  .timeout(<span class="integer">3</span>, <span class="predefined-type">TimeUnit</span>.Seconds)
  .map(<span class="local-variable">this</span>::convert)
  .dispatchOn(cachedDispatcher());
  .subscribeOn(workDispatcher());

stream
  .buffer(<span class="integer">5</span>, <span class="integer">200</span>, <span class="predefined-type">TimeUnit</span>.MILLISECONDS)
  .consume(<span class="predefined-type">System</span>.out::println);</code></pre>
</div>
</div></div></td>
</tr>
<tr>
<th class="tableblock halign-center valign-middle" colspan="2"><p class="tableblock">The Result</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><div><div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p>Yes it&#8217;s more verbose&#8230;&#8203;</p>
</li>
<li>
<p>&#8230;&#8203;But now we stream result by result from the query (could have used pagination with SQL limits as well).</p>
</li>
<li>
<p><code>Streams.createWith</code> is a <code>PublisherFactory</code> which intercepts requests, start and stop.</p>
<div class="ulist">
<ul>
<li>
<p>The request consumer gives precisely how many elements a subscriber is ready to receive.</p>
</li>
<li>
<p>The request consumer receives a <code>SubscriberWithContext</code> delegating to the real <code>Subscriber</code>, it gives access to shared context and cancel status.</p>
</li>
<li>
<p>We send at most as many individual <em>Result</em> as demanded</p>
</li>
<li>
<p>We complete when the query read is fully processed</p>
</li>
</ul>
</div>
</li>
<li>
<p>Since the data is individual now, convertToList is unecessary, replaced with convert</p>
</li>
<li>
<p>The Consuming aspect can start using tools such as <code>capacity(long)</code> or <code>buffer(int)</code> to batch consume the request 5 by 5.</p>
<div class="ulist">
<ul>
<li>
<p>As a result the flow will be perceived faster because we don&#8217;t print after every rows have been read</p>
</li>
<li>
<p>We add a time limit to the batch since it might not match with the size</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
It&#8217;s important to balance the use of stateful <code>Iterable&lt;T&gt;</code> like <code>List&lt;T&gt;</code> vs individual streaming <code>T</code>. A <code>List</code> might incur at some point more latency since we take more time to create it. It&#8217;s also not playing that well in favor of resiliency since it&#8217;s a whole batch we can lose if a fatal error occurs. Finally, streaming <code>T</code> data makes sizing demand more predictable because we can score individual signals instead of batches of signals.
</td>
</tr>
</table>
</div></div></td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
<div class="sect1">
<h2 id="streams-errors">Error Handling</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Since error isolation is an important part of the <strong>Reactive</strong> contract, <code>Stream</code> API is equipped to build fault tolerant pipelines or service call.</p>
</div>
<div class="paragraph">
<p>Error isolation comes simply by preventing <code>onNext</code>, <code>onSubscribe</code> and <code>onComplete</code> callbacks to bubble up any exception. Instead they are passed to the <code>onError</code> callback and propagated downstream. A few <code>Action</code> can react passively or actively on such signal, e.g. <code>when()</code> will just observe errors and <code>onErrorResumeNext()</code> will switch to a fallback <code>Publisher</code>.</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="paragraph">
<p>Inversing the propagation to the consuming side instead of bubbling up to the producer side is the reactive pattern to isolate the data producer from the pipeline errors and keep producers alive and happy.</p>
</div>
</div>
</div>
<div class="paragraph">
<p>In the end the last <code>Subscriber</code> in the chain will be notified with the <code>onError(t)</code> callback method. If that <code>Subscriber</code> is a <code>ConsumerAction</code> for instance, Reactor will re-route an error if no <em>errorConsumer</em> callback has been assigned using <code>Stream.consume(dataConsumer, errorConsumer)</code>. The route will trigger the current <code>Environment</code> error journal if set, which by default uses SLF4J to log errors.</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="paragraph">
<p><strong>Reactor</strong> also distinguishes <strong>fatal exceptions</strong> from normal ones, specially during <code>onSubscribe</code> process. These exceptions will not be isolated nor passed downstream to the subscriber(s) :</p>
</div>
<div class="ulist">
<ul>
<li>
<p>CancelException</p>
<div class="ulist">
<ul>
<li>
<p>Happens if no subscriber is available during <code>onNext</code> propagation, e.g. when a subscriber asynchronously cancelled during <code>onNext</code> emission</p>
</li>
<li>
<p>Use the JVM property <strong>-Dreactor.trace.cancel=true</strong> to enable verbose CancelException and logging in Environment default journal. If not set, Environment will not report these exceptions and there won&#8217;t be any stacktrace associated neither.</p>
</li>
</ul>
</div>
</li>
<li>
<p>ReactorFatalException</p>
<div class="ulist">
<ul>
<li>
<p>Happens when Reactor defines an unrecoverable situation like a scheduling on <code>Timer</code> not matching the resolution.</p>
</li>
</ul>
</div>
</li>
<li>
<p>JVM unsafe exceptions:</p>
<div class="ulist">
<ul>
<li>
<p>StackOverflowError</p>
</li>
<li>
<p>VirtualMachineError</p>
</li>
<li>
<p>ThreadDeath</p>
</li>
<li>
<p>LinkageError</p>
</li>
</ul>
</div>
</li>
</ul>
</div>
</div>
</div>
<div class="paragraph">
<p>A good practice as seen in various sections is to set time limits explicitely, so <code>timeout()</code> + <code>retry()</code> will be your best mates especially to protect against network partitioning. The more data flows in the <code>Stream</code> the better it should be able to auto heal to keep a good service availability.</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
In Reactive Streams, at most one error can traverse a pipeline, so you can&#8217;t really double <code>onError(e)</code> a <code>Subsriber</code>, in theory. In practice we implemented the <em>Rx</em> operators <code>retry()</code> and <code>retryWhen()</code> that will cancel/re-subscribe <code>onError</code>. That means we still respect the contract as an entire new pipeline will be materialized transparently, with fresh action instances. That also means stateful <code>Action</code> like <code>buffer()</code> should be used with caution in this scenario since we just de-reference them, their state might be lost. We are working on alternatives, one of them involving external persistence for safe stateful <code>Actions</code>. A glimpse of that can be read in the <a href="#streams-persistent">related section</a>.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Fallback cascade fun</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Broadcaster&lt;<span class="predefined-type">String</span>&gt; broadcaster = Broadcaster.create();

Promise&lt;<span class="predefined-type">List</span>&lt;<span class="predefined-type">String</span>&gt;&gt; promise =
    broadcaster
        .timeout(<span class="integer">1</span>, <span class="predefined-type">TimeUnit</span>.SECONDS, Streams.fail(<span class="keyword">new</span> <span class="exception">Exception</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">another one!</span><span class="delimiter">&quot;</span></span>))) <i class="conum" data-value="1"></i><b>(1)</b>
        .onErrorResumeNext(Streams.just(<span class="string"><span class="delimiter">&quot;</span><span class="content">Alternative Message</span><span class="delimiter">&quot;</span></span>)) <i class="conum" data-value="2"></i><b>(2)</b>
        .toList();

broadcaster.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">test1</span><span class="delimiter">&quot;</span></span>);
broadcaster.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">test2</span><span class="delimiter">&quot;</span></span>);
<span class="predefined-type">Thread</span>.sleep(<span class="integer">1500</span>);

<span class="keyword">try</span> {
  broadcaster.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">test3</span><span class="delimiter">&quot;</span></span>);
} <span class="keyword">catch</span> (CancelException ce) {
  <span class="comment">//Broadcaster has no subscriber, timeout disconnected the pipeline</span>
}

promise.await();

assertEquals(promise.get().get(<span class="integer">0</span>), <span class="string"><span class="delimiter">&quot;</span><span class="content">test1</span><span class="delimiter">&quot;</span></span>);
assertEquals(promise.get().get(<span class="integer">1</span>), <span class="string"><span class="delimiter">&quot;</span><span class="content">test2</span><span class="delimiter">&quot;</span></span>);
assertEquals(promise.get().get(<span class="integer">2</span>), <span class="string"><span class="delimiter">&quot;</span><span class="content">Alternative Message</span><span class="delimiter">&quot;</span></span>);</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td><code>TimeoutAction</code> can fallback when no data is emited for the given time period, but in this case it will just emit another Exception&#8230;&#8203;</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>&#8230;&#8203;However, we are lucky to have <code>onErrorResumeNext(Publisher)</code> to catch this exception and actually deliver some String payload</td>
</tr>
</table>
</div>
<div class="paragraph">
<p>Another classic example of fault-tolerant pipeline can be found in <a href="#recipes-circuitbreaker">Recipes Section</a>.</p>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 18. Handling errors</caption>
<colgroup>
<col style="width: 100%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt; API</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">when(Class&lt;Throwable&gt;, Consumer&lt;Throwable&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Observe specific exception types (and their hierarchy) coming from <code>onError(Throwable)</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">oberveError(Class&lt;Throwable&gt;, BiConsumer&lt;Object,Throwable&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Similar to <code>when</code> but allows introspection of the failing <code>onNext(Object)</code> if any when the exception originally rose.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">onErrorReturn(<em>Class&lt;Throwable</em>, Function&lt;Throwable,T&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Provide a fallback signal <code>T</code> given an exception matching the passed type otherwise any exception. Commonly use in self-healing services.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">onErrorResume(<em>Class&lt;Throwable</em>, Publisher&lt;T&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Provide a fallback sequence of signal <code>T</code> given an exception matching the passed type otherwise any exception. Commonly use in self-healing services.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">materialize() <em>dematerialize()</em></p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Transform upstream signal into <code>Signal&lt;T&gt;</code>, and treat them as <code>onNext(Signal&lt;T&gt;)</code> signals. The immediate effect: it swallows error and completion signals, so it&#8217;s an effective way to process errors. Once errors are processed we can still run them by transforming the <code>Signal&lt;T&gt;</code> into the Reactive Streams right callback via <code>dematerialize()</code>.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">retry(<em>int, Predicate&lt;Throwable</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Cancel/Re-Subscribe the parent <code>Stream</code> up to the optional <em>tries</em> argument and matching the passed <code>Predicate</code> if provided.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">retryWhen(Function&lt;Stream&lt;Throwable&gt;,Publisher&lt;?&gt;&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Cancel/Re-Subscribe the parent <code>Stream</code> when the returned <code>Publisher</code> from the passed <code>Function</code> emits <code>onNext(Object)</code>. The function is called once on subscribe and the generated <code>Publisher</code> is subscribed. If the <code>Publisher</code> emits <code>onError(e)</code> or <code>onComplete()</code>, they will be propagated downstream. The <code>Function</code> receives a single <code>Stream</code> of errors which have occured in any subscribed pipeline. Can be combined with <strong>counting</strong> and <strong>delaying</strong> actions to provide for bounded and exponantial retry strategies.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">recover(Class&lt;Throwable&gt;, Subscriber&lt;Object&gt;)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">A <code>retryWhen()</code> shortcut to re-subscribe parent Publisher if the <code>onError(Throwable)</code> matches the given type. On recovery success, the passed <code>Subscriber</code> argument will receive the <code>onNext(Object)</code> that was the root signal associated with the exception, if any.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">ignoreError(<em>Predicate&lt;Throwable&gt;</em>)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Transform the matching <code>onError(Throwable)</code> signals into <code>onComplete()</code>. If no argument has been provided, just transform any error into completion.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock"><strong>throw</strong> CancelException</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">That might be the only time we will mention anything related to exception bubbling up. However throwing <code>CancelException.INSTANCE</code> in any <code>onNext(T)</code> callback is a simple way to <strong>no-ack</strong> an incoming value and inform colocated (within the same thread stack) Publishers like <strong>Core Processor</strong> they might have to re-schedule this data later.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="sect1">
<h2 id="streams-persistent">Persisting Stream Data</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Not everything has to be in-memory and <code>Reactor</code> has started a story to integrate (optional dependency) with <a href="https://github.com/OpenHFT/Chronicle-Queue">Java Chronicle</a>.</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="keyword">return</span> Streams.merge(
  userService.filteredFind(<span class="string"><span class="delimiter">&quot;</span><span class="content">Rick</span><span class="delimiter">&quot;</span></span>),
  userService.filteredFind(<span class="string"><span class="delimiter">&quot;</span><span class="content">Morty</span><span class="delimiter">&quot;</span></span>)
)
.buffer()
.retryWhen( errors -&gt;
  errors
  .zipWith(Streams.range(<span class="integer">1</span>,<span class="integer">3</span>), t -&gt; t.getT2())
  .flatMap( tries -&gt; Streams.timer(tries) )
)
.consume(<span class="predefined-type">System</span>.out::println);</code></pre>
</div>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 19. Persisting signals safely</caption>
<colgroup>
<col style="width: 100%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Functional API or Factory method</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream.onOverflowBuffer(CompletableQueue)</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">IOStreams.persistentMapReader()</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">IOStreams.persistentMap()</p></th>
</tr>
<tr>
<td class="tableblock halign-left valign-top"></td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="sect1">
<h2 id="streams-analytics">Analytics</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Metrics and other stateful operations are fully part of the <code>Stream</code> API. Users familiar with <code>Spark</code> will recognize some method names in fact. <code>ScanAction</code> also offers a popular accumulating functional contract with <code>reduce()</code> and <code>scan()</code>.</p>
</div>
<div class="listingblock">
<div class="title">Playing with metrics and key/value data</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">Broadcaster&lt;<span class="predefined-type">Integer</span>&gt; source = Broadcaster.&lt;<span class="predefined-type">Integer</span>&gt; create(Environment.get());
<span class="type">long</span> avgTime = <span class="integer">50l</span>;

Promise&lt;<span class="predefined-type">Long</span>&gt; result = source
    .throttle(avgTime) <i class="conum" data-value="1"></i><b>(1)</b>
    .elapsed() <i class="conum" data-value="2"></i><b>(2)</b>
    .nest() <i class="conum" data-value="3"></i><b>(3)</b>
    .flatMap(self -&gt;
            BiStreams.reduceByKey(self, (prev, next) -&gt; prev + <span class="integer">1</span>) <i class="conum" data-value="4"></i><b>(4)</b>
    )
    .sort((a,b) -&gt; a.t1.compareTo(b.t1)) <i class="conum" data-value="5"></i><b>(5)</b>
    .log(<span class="string"><span class="delimiter">&quot;</span><span class="content">elapsed</span><span class="delimiter">&quot;</span></span>)
    .reduce(-<span class="integer">1L</span>, (acc, next) -&gt;
            acc &gt; <span class="integer">0l</span> ? ((next.t1 + acc) / <span class="integer">2</span>) : next.t1 <i class="conum" data-value="6"></i><b>(6)</b>
    )
    .next(); <i class="conum" data-value="7"></i><b>(7)</b>

<span class="keyword">for</span> (<span class="type">int</span> i = <span class="integer">0</span>; i &lt; <span class="integer">10</span>; i++) {
  source.onNext(<span class="integer">1</span>);
}
source.onComplete();</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Slow down incoming <code>Subscriber</code> request to one every ~50 milliseconds, polling waiting data one by one.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Produce a <code>Tuple2</code> of <strong>Time delta</strong> and <strong>payload</strong> between 2 signals or between <code>onSubscribe</code> and the first signal.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Make the current <code>Stream</code> available with <code>onNext</code> so we can compose it with a <code>flatMap</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Accumulate all data until <code>onComplete()</code> in internal <code>Map</code> keyed with the <code>Tuple2.t1</code> and valued by default with <code>Tuple2.t2</code>. Next matching keys will provide the previous value and the incoming new <code>onNext</code> in the accumulator <code>BiFunction</code>. In this case we only increment the initial payload <em>1</em> by key.</td>
</tr>
<tr>
<td><i class="conum" data-value="5"></i><b>5</b></td>
<td>Accumulate all data until <code>onComplete()</code> in internal <code>PriorityQueue</code> and sort elapsed time <em>t1</em> using the given comparator. After <code>onComplete()</code> all data are emitted in order, then complete.</td>
</tr>
<tr>
<td><i class="conum" data-value="6"></i><b>6</b></td>
<td>Accumulate until <code>onComplete</code> a moving time average defaulting to the first received time.</td>
</tr>
<tr>
<td><i class="conum" data-value="7"></i><b>7</b></td>
<td>Take the next and only produced average.</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Output</div>
<div class="content">
<pre>03:14:42.013 [main] INFO  elapsed - subscribe: ScanAction
03:14:42.021 [main] INFO  elapsed - onSubscribe: {push}
03:14:42.022 [main] INFO  elapsed - request: 9223372036854775807
03:14:42.517 [hash-wheel-timer-run-3] INFO  elapsed - onNext: 44,1
03:14:42.518 [hash-wheel-timer-run-3] INFO  elapsed - onNext: 48,1
03:14:42.518 [hash-wheel-timer-run-3] INFO  elapsed - onNext: 49,2
03:14:42.518 [hash-wheel-timer-run-3] INFO  elapsed - onNext: 50,3
03:14:42.518 [hash-wheel-timer-run-3] INFO  elapsed - onNext: 51,3
03:14:42.519 [hash-wheel-timer-run-3] INFO  elapsed - complete: SortAction
03:14:42.520 [hash-wheel-timer-run-3] INFO  elapsed - cancel: SortAction</pre>
</div>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 20. Operations useful for metrics and other stateful accumulation.</caption>
<colgroup>
<col style="width: 85%;">
<col style="width: 14%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt; API or Factory method</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Output Type</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">count()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Long</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Produce the total number of observed <code>onNext(T)</code> after observing <code>onComplete()</code>. Useful when combined with timed <code>windows</code>. Not so useful with sized <code>windows</code>, e.g. <code>stream.window(5).flatMap(w -&gt; w.count())</code> &#8594; produce 5, awesome.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">scan(BiFunction&lt;T,T&gt;)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">scan(A, BiFunction&lt;A,T&gt;)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">A</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">reduce(BiFunction&lt;T,T&gt;)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">reduce(A, BiFunction&lt;A,T&gt;)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">A</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">BiStreams.reduceByKey()</p></th>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">BiStreams.scanByKey()</p></th>
<td class="tableblock halign-left valign-top"></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">timestamp()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Tuple2&lt;Long,T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">elapsed()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Tuple2&lt;Long,T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">materialize() <em>dematerialize()</em></p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Signal&lt;T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Transform upstream signal into <code>Signal&lt;T&gt;</code>, and treat them as <code>onNext(Signal&lt;T&gt;)</code> signals. The immediate effect: it swallows error and completion signals, so it&#8217;s an effective way to count errors and completions if the <code>Stream</code> is using <code>retry</code> or <code>repeat</code> API. Once completion and errors are processed we can still run them by transforming the <code>Signal&lt;T&gt;</code> into the Reactive Streams right callback via <code>dematerialize()</code>.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="sect1">
<h2 id="streams-partition">Partitioning</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Partition a <code>Stream</code> for concurrent, parallel work.</p>
</div>
<div class="paragraph">
<p>An important aspect of the functional composition approach to reactive programming is that work can be broken up into discreet chunks and scheduled to run on arbitrary Dispatchers. This means you can easily compose a flow of work that starts with an input value, executes work on another thread, and then passes through subsequent transformation steps once the result is available. This is one of the more common usage patterns with Reactor.</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">DispatcherSupplier supplier1 = Environment.newCachedDispatchers(<span class="integer">2</span>, <span class="string"><span class="delimiter">&quot;</span><span class="content">groupByPool</span><span class="delimiter">&quot;</span></span>);
DispatcherSupplier supplier2 = Environment.newCachedDispatchers(<span class="integer">5</span>, <span class="string"><span class="delimiter">&quot;</span><span class="content">partitionPool</span><span class="delimiter">&quot;</span></span>);

Streams
    .range(<span class="integer">1</span>, <span class="integer">10</span>)
    .groupBy(n -&gt; n % <span class="integer">2</span> == <span class="integer">0</span>) <i class="conum" data-value="1"></i><b>(1)</b>
    .flatMap(stream -&gt; stream
            .dispatchOn(supplier1.get()) <i class="conum" data-value="2"></i><b>(2)</b>
            .log(<span class="string"><span class="delimiter">&quot;</span><span class="content">groupBy</span><span class="delimiter">&quot;</span></span>)
    )
    .partition(<span class="integer">5</span>) <i class="conum" data-value="3"></i><b>(3)</b>
    .flatMap(stream -&gt; stream
            .dispatchOn(supplier2.get()) <i class="conum" data-value="4"></i><b>(4)</b>
            .log(<span class="string"><span class="delimiter">&quot;</span><span class="content">partition</span><span class="delimiter">&quot;</span></span>)
    )
    .dispatchOn(Environment.sharedDispatcher()) <i class="conum" data-value="5"></i><b>(5)</b>
    .log(<span class="string"><span class="delimiter">&quot;</span><span class="content">join</span><span class="delimiter">&quot;</span></span>)
    .consume();</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Create at most two streams (odd/even) keyed by 0 or 1 and forward the <code>onNext(T)</code> to the matching one.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Add one of the pooled dispatchers for the two emitted <code>Stream</code> by previous <code>GroupByAction</code>. Effectively this is scaling up a stream by using 2 partitions assigned with their own dispatcher. <code>FlatMap</code> will merge the result returned by both partitions, running on one of the two threads, but never concurrently.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Create 5 Streams and forward <code>onNext(T)</code> to them in a round robin fashion</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Use the second dispatcher pool of 5 to assign to the newly generated streams. The returned sequences will be merged.</td>
</tr>
<tr>
<td><i class="conum" data-value="5"></i><b>5</b></td>
<td>Dispatch data on the <code>Environment.sharedDispatcher()</code>, so neither the first or the second pool. The 5 threads will then be merged under the <code>Dispatcher</code> thread</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Output extract</div>
<div class="content">
<pre>03:53:42.060 [groupByPool-3] INFO  groupBy - onNext: 4
03:53:42.060 [partitionPool-8] INFO  partition - onNext: 9
03:53:42.061 [groupByPool-3] INFO  groupBy - onNext: 6
03:53:42.061 [partitionPool-8] INFO  partition - onNext: 4
03:53:42.061 [shared-1] INFO  join - onNext: 9
03:53:42.061 [groupByPool-3] INFO  groupBy - onNext: 8
03:53:42.061 [partitionPool-4] INFO  partition - onNext: 6
03:53:42.061 [shared-1] INFO  join - onNext: 4
03:53:42.061 [groupByPool-3] INFO  groupBy - onNext: 10
03:53:42.061 [shared-1] INFO  join - onNext: 6
03:53:42.061 [groupByPool-3] INFO  groupBy - complete: DispatcherAction</pre>
</div>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 21. Grouping operations</caption>
<colgroup>
<col style="width: 85%;">
<col style="width: 14%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt; API</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Output Type</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">groupBy(Function&lt;T,K&gt;)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">GroupedStream&lt;K,T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">partition(int)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">GroupedStream&lt;K,T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock"><em>All</em> window(<em>arguments</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt;</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock"><a href="#streams-microbatching">Windows</a> are actually for cutting partitions over time, size or coordinated with external signals.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">process(XXXWorkProcessor)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="2"><p class="tableblock">Since a RingBufferWorkProcessor distributes the signals to each subscribe, it is an efficient alternative to <code>partition()</code> when its just about scaling-up, not routing.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<div class="sect1">
<h2 id="streams-notrx">Other API beyond Rx</h2>
<div class="sectionbody">
<div class="paragraph">
<p>In addition to implementing directly the Reactive Streams, some more <code>Stream</code> methods not covered differ or are simply not documented by Reactive Extensions.</p>
</div>
<table class="tableblock frame-all grid-all spread">
<caption class="title">Table 22. Other methods uncovered in the previous use cases.</caption>
<colgroup>
<col style="width: 75%;">
<col style="width: 12%;">
<col style="width: 12%;">
</colgroup>
<tbody>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">Stream&lt;T&gt; API</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Input Type</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Output Type</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Role</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">after()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">Void</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Only consume <code>onComplete()</code> and <code>onError(Throwable)</code> signals.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">log(<em>String</em>)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Use SLF4J and the given category to log each signal.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">split</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">Iterable&lt;T&gt;</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Blocking transformation from <code>Iterable&lt;T&gt;</code> to as many <code>onNext(T)</code> as available.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">sort(<em>int</em>, Comparator&lt;T&gt;)</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Accept up to the given size into an in memory <code>PriorityQueue</code>, apply the <code>Comparator&lt;T&gt;</code> to sort, and emit all its pending <code>onNext(T)</code> signals.</p></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">combine()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">I</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">O</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><div><div class="paragraph">
<p>Scan for the most ancient parent or <code>Action</code>, from right to left. As a result, it will create a new <code>Processor</code> with the input <code>onXXXX</code> signals dispatched to the old action and the output <code>subscribe</code> delegated to the current action.</p>
</div>
<div class="paragraph">
<p>Example:</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="predefined-type">Action</span>&lt;<span class="predefined-type">Integer</span>, <span class="predefined-type">String</span>&gt; processor = stream
  .filter( i -&gt; i&lt;<span class="integer">2</span> )
  .map(<span class="predefined-type">Object</span>::toString)
  .combine();

  processor.consume(<span class="predefined-type">System</span>.out::println);
  processor.onNext(<span class="integer">1</span>);
  processor.onNext(<span class="integer">3</span>);</code></pre>
</div>
</div></div></td>
</tr>
<tr>
<th class="tableblock halign-left valign-top"><p class="tableblock">keepAlive()</p></th>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
<td class="tableblock halign-left valign-top"><p class="tableblock">T</p></td>
</tr>
<tr>
<td class="tableblock halign-left valign-top" colspan="3"><p class="tableblock">Prevent any <code>Subscription.cancel()</code> to propagate from the <code>Subscriber</code>.</p></td>
</tr>
</tbody>
</table>
</div>
</div>
<h1 id="reactor-bus" class="sect0"><strong>reactor-bus</strong></h1>
<div class="sect1">
<h2 id="bus">Routing data</h2>
<div class="sectionbody">
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/bus-overview.png"><img src="images/bus-overview.png" alt="Stream Overview" width="500"></a>
</div>
<div class="title">Figure 14. How Doge can use Reactor-Bus</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="bus-publish-subscribe">Publish/Subscribe</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Using an <code>EventBus</code> to publish and respond to events using Publish/Subscribe.</p>
</div>
<div class="paragraph">
<p>Reactor&#8217;s <code>EventBus</code> allows you to register a <code>Consumer</code> to handle events when the notification key matches a certain condition. This assignment is achieved via the <code>Selector</code>. It&#8217;s similar to subscribing to a topic, though Reactor&#8217;s <code>Selector</code> implementations can match on a variety of critera, from <code>Class&lt;?&gt;</code> type to regexes, to <code>JsonPath</code> expressions. It is a very flexible and powerful abstraction that provides a wide range of possibilities.</p>
</div>
<div class="paragraph">
<p>You can register multiple Consumers using the same <code>Selector</code> and multiple <code>Selectors</code> can match a given key. This way it&#8217;s easy to do aggregation and broadcasting: you simply subscribe multiple <code>Consumers</code> to the same topic <code>Selector</code>.</p>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
<div class="paragraph">
<p>If you&#8217;re upgrading from Reactor 1.1, you&#8217;ll see that the <code>Reactor</code> class no longer exists. It has been renamed to <code>EventBus</code> to more accurately reflect its role in the framework.</p>
</div>
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Handling events using a Selector</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">EventBus bus = EventBus.create(Environment.get()); <i class="conum" data-value="1"></i><b>(1)</b>

bus.on(<span class="error">$</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">topic</span><span class="delimiter">&quot;</span></span>), (<span class="predefined-type">Event</span>&lt;<span class="predefined-type">String</span>&gt; ev) -&gt; {
  <span class="predefined-type">String</span> s = ev.getData();
  <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">Got %s on thread %s%n</span><span class="delimiter">&quot;</span></span>, s, <span class="predefined-type">Thread</span>.currentThread());
}); <i class="conum" data-value="2"></i><b>(2)</b>

bus.notify(<span class="string"><span class="delimiter">&quot;</span><span class="content">topic</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Event</span>.wrap(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello World!</span><span class="delimiter">&quot;</span></span>)); <i class="conum" data-value="3"></i><b>(3)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Create an <code>EventBus</code> using the default, shared <code>RingBufferDispatcher</code> from the static <code>Environment</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Assign a <code>Consumer</code> to invoke when the <code>EventBus</code> is notified with a key that matches the <code>Selector</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Publish an <code>Event</code> into the <code>EventBus</code> using the given topic.</td>
</tr>
</table>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
<div class="paragraph">
<p>The shorthand static method <code>$</code> is just a convenience helper that is identical to <code>Selectors.object()</code>. Some people don&#8217;t like to use the shorthand methods like <code>$()</code> for <code>ObjectSelector</code>, <code>R()</code> for <code>RegexSelector</code>, <code>T()</code> for <code>ClassSelector</code>, and so forth. The <a href="/docs/api/reactor/bus/selector/Selectors.html#method.summary">Selectors</a> class has longer method name alternatives for these shorthand versions, which are simply aliases to reduce code noise and make reactive code a little more readable.</p>
</div>
</td>
</tr>
</table>
</div>
</div>
</div>
<div class="sect1">
<h2 id="bus-request-reply">Request/Reply</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Using an <code>EventBus</code> to publish and respond to events using Request/Reply.</p>
</div>
<div class="paragraph">
<p>It&#8217;s often the case that you want to receive a reply from a task executed on an EventBus&#8217;s configured <code>Dispatcher</code>. Reactor&#8217;s <code>EventBus</code> provides for more event handling models beyond the simple publish/subscribe model. You can also register a <code>Function</code> rather than a <code>Consumer</code> and have the <code>EventBus</code> automatically notify a <code>replyTo</code> key of the return value of the <code>Function</code>. Rather than using the <code>.on()</code> and <code>.notify()</code> methods, you use the <code>.receive()</code>, and <code>.send()</code> methods.</p>
</div>
<div class="listingblock">
<div class="title">Request/Reply</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">EventBus bus;

bus.on(<span class="error">$</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">reply.sink</span><span class="delimiter">&quot;</span></span>), ev -&gt; {
  <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">Got %s on thread %s%n</span><span class="delimiter">&quot;</span></span>, ev, <span class="predefined-type">Thread</span>.currentThread())
}); <i class="conum" data-value="1"></i><b>(1)</b>

bus.receive(<span class="error">$</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">job.sink</span><span class="delimiter">&quot;</span></span>), ev -&gt; {
  <span class="keyword">return</span> doWork(ev);
}); <i class="conum" data-value="2"></i><b>(2)</b>

bus.send(<span class="string"><span class="delimiter">&quot;</span><span class="content">job.sink</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Event</span>.wrap(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello World!</span><span class="delimiter">&quot;</span></span>, <span class="string"><span class="delimiter">&quot;</span><span class="content">reply.sink</span><span class="delimiter">&quot;</span></span>)); <i class="conum" data-value="3"></i><b>(3)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Assign a <code>Consumer</code> to handle all replies indiscriminantly.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Assign a <code>Function</code> to perform work in the <code>Dispatcher</code> thread and return a result.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Publish an <code>Event</code> into the bus using the given <code>replyTo</code> key.</td>
</tr>
</table>
</div>
<div class="paragraph">
<p>If you don&#8217;t have a generic topic on which to publish replies, you can combine the request and reply operation into a single call using the <code>.sendAndReceive(Object, Event&lt;?&gt;, Consumer&lt;Event&lt;?&gt;&gt;)</code> method. This performs a <code>.send()</code> call and invokes the given replyTo callback on the <code>Dispatcher</code> thread when the Functions are invoked.</p>
</div>
<div class="listingblock">
<div class="title">sendAndReceive()</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">EventBus bus;

bus.receive(<span class="error">$</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">job.sink</span><span class="delimiter">&quot;</span></span>), (<span class="predefined-type">Event</span>&lt;<span class="predefined-type">String</span>&gt; ev) -&gt; {
  <span class="keyword">return</span> ev.getData().toUpperCase();
}); <i class="conum" data-value="1"></i><b>(1)</b>

bus.sendAndReceive(
    <span class="string"><span class="delimiter">&quot;</span><span class="content">job.sink</span><span class="delimiter">&quot;</span></span>,
   <span class="predefined-type">Event</span>.wrap(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello World!</span><span class="delimiter">&quot;</span></span>),
   s -&gt; <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">Got %s on thread %s%n</span><span class="delimiter">&quot;</span></span>, s, <span class="predefined-type">Thread</span>.currentThread())
); <i class="conum" data-value="2"></i><b>(2)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Assign a <code>Function</code> to perform work in the <code>Dispatcher</code> thread and return a result.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Publish an <code>Event</code> into the bus and schedule the given replyTo <code>Consumer</code> on the <code>Dispatcher</code>, passing the receive Function&#8217;s result as input.</td>
</tr>
</table>
</div>
<div class="sect2">
<h3 id="_cancelling_a_task">Cancelling a Task</h3>
<div class="paragraph">
<p>Sometimes you want to cancel a task to cause it to stop responding to event notifications. The registration methods <code>.on()</code> and <code>.receive()</code> return a <code>Registration</code> object which, if a reference to it is held, can be used later to cancel a <code>Consumer</code> or <code>Function</code> for a given <code>Selector</code>.</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">EventBus bus;

Registration reg = bus.on(<span class="error">$</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">topic</span><span class="delimiter">&quot;</span></span>),
                          s -&gt; <span class="predefined-type">System</span>.out.printf(<span class="string"><span class="delimiter">&quot;</span><span class="content">Got %s on thread %s%n</span><span class="delimiter">&quot;</span></span>, s, <span class="predefined-type">Thread</span>.currentThread()));

bus.notify(<span class="string"><span class="delimiter">&quot;</span><span class="content">topic</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Event</span>.wrap(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello World!</span><span class="delimiter">&quot;</span></span>)); <i class="conum" data-value="1"></i><b>(1)</b>

<span class="comment">// ...some time later...</span>
reg.cancel(); <i class="conum" data-value="2"></i><b>(2)</b>

<span class="comment">// ...some time later...</span>
bus.notify(<span class="string"><span class="delimiter">&quot;</span><span class="content">topic</span><span class="delimiter">&quot;</span></span>, <span class="predefined-type">Event</span>.wrap(<span class="string"><span class="delimiter">&quot;</span><span class="content">Hello World!</span><span class="delimiter">&quot;</span></span>)); <i class="conum" data-value="3"></i><b>(3)</b></code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Publish an event to the given topic. Should print <code>Event.toString()</code> in the console.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Cancel the <code>Registration</code> to prevent further events from reaching the <code>Consumer</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Nothing should happen as a result of this notification.</td>
</tr>
</table>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
<div class="paragraph">
<p>Keep in mind that cancelling a <code>Registration</code> involves accessing the internal <code>Registry</code> in an atomic way. In a system in which a large number of events are flowing into Consumers, it&#8217;s likely that your <code>Consumer</code> or <code>Function</code> might see some values after you&#8217;ve invoked the <code>.cancel()</code> method, but before the <code>Registry</code> has had a chance to clear the caches and remove the <code>Registration</code>. The <code>.cancel()</code> method could be described as a "request to cancel as soon as possible".</p>
</div>
<div class="paragraph">
<p>You&#8217;ll notice this behavior right away in test classes where there&#8217;s no time delay between the <code>.on()</code>, <code>.notify()</code>, and <code>.cancel()</code> invocations.</p>
</div>
</td>
</tr>
</table>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="bus-registry">Registry</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Using a <code>Registry</code> to cache in-memory values.</p>
</div>
</div>
</div>
<h1 id="reactor-net" class="sect0"><strong>reactor-net</strong></h1>
<div class="sect1">
<h2 id="_asynchronous_tcp_udp_and_http">Asynchronous TCP, UDP and HTTP</h2>
<div class="sectionbody">
<div class="quoteblock">
<blockquote>
Nothing travels faster than the speed of light, with the possible exception of bad news, which obeys its own special laws.
</blockquote>
<div class="attribution">
&#8212; Douglas Noel Adams<br>
<cite>Mostly Harmless (1992)</cite>
</div>
</div>
<div class="listingblock">
<div class="title">Head first with a Java 8 example of some Net work</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="keyword">import</span> <span class="include">reactor.io.net.NetStreams</span>;
<span class="keyword">import</span> <span class="include">reactor.io.net.tcp.TcpServer</span>;
<span class="keyword">import</span> <span class="include">reactor.io.net.tcp.TcpClient</span>;

<span class="comment">//...</span>

<span class="predefined-type">CountDownLatch</span> latch = <span class="keyword">new</span> <span class="predefined-type">CountDownLatch</span>(<span class="integer">10</span>);

TcpServer&lt;<span class="predefined-type">Buffer</span>, <span class="predefined-type">Buffer</span>&gt; server = NetStreams.tcpServer(port);
TcpClient&lt;<span class="predefined-type">Buffer</span>, <span class="predefined-type">Buffer</span>&gt; client = NetStreams.tcpClient(<span class="string"><span class="delimiter">&quot;</span><span class="content">localhost</span><span class="delimiter">&quot;</span></span>, port);

<span class="directive">final</span> JsonCodec&lt;Pojo, Pojo&gt; codec = <span class="keyword">new</span> JsonCodec&lt;Pojo, Pojo&gt;(Pojo.class);

<span class="comment">//the client/server are prepared</span>
server.start( input -&gt;

        <span class="comment">//for each connection echo any incoming data</span>

        <span class="comment">//return the write confirm publisher from writeWith</span>
        <span class="comment">// &gt;&gt;&gt; close when the write confirm completed</span>

        input.writeWith(

                <span class="comment">//read incoming data</span>
                input
                        .decode(codec) <span class="comment">//transform Buffer into Pojo</span>
                        .log(<span class="string"><span class="delimiter">&quot;</span><span class="content">serve</span><span class="delimiter">&quot;</span></span>)
                        .map(codec)    <span class="comment">//transform Pojo into Buffer</span>
                        .capacity(<span class="integer">5l</span>)  <span class="comment">//auto-flush every 5 elements</span>
        )
).await();

client.start( input -&gt; {

        <span class="comment">//read 10 replies and close</span>
        input
                .take(<span class="integer">10</span>)
                .decode(codec)
                .log(<span class="string"><span class="delimiter">&quot;</span><span class="content">receive</span><span class="delimiter">&quot;</span></span>)
                .consume( data -&gt; latch.countDown() );

        <span class="comment">//write data</span>
        input.writeWith(
                Streams.range(<span class="integer">1</span>, <span class="integer">10</span>)
                        .map( it -&gt; <span class="keyword">new</span> Pojo(<span class="string"><span class="delimiter">&quot;</span><span class="content">test</span><span class="delimiter">&quot;</span></span> + it) )
                        .log(<span class="string"><span class="delimiter">&quot;</span><span class="content">send</span><span class="delimiter">&quot;</span></span>)
                        .map(codec)
        );

        <span class="comment">//keep-alive, until 10 data have been read</span>
        <span class="keyword">return</span> Streams.never();

}).await();

latch.await(<span class="integer">10</span>, <span class="predefined-type">TimeUnit</span>.SECONDS);

client.shutdown().await();
server.shutdown().await();</code></pre>
</div>
</div>
<div class="sect2">
<h3 id="net-overview">Overview</h3>
<div class="paragraph">
<p>How is Reactor Net module working ?</p>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/net-overview.png"><img src="images/net-overview.png" alt="Net Overview" width="650"></a>
</div>
<div class="title">Figure 15. How Doge can use Reactor-Net</div>
</div>
<div class="paragraph">
<p>So why should you care about an asynchronous runtime to deal with network operations ? As seen in the <a href="#streams-microservice">Microservice with Streams</a> section, it is preferred to not block for a service reply. Non-Blocking write over network will slightly be more costly than blocking ones in terms of resources, however it might be perceived <strong>more responsive</strong> to the producer. Responsiveness all along the request flow impacts various systems and eventually, 1 or N users waiting their turn to push new requests.</p>
</div>
<div class="imageblock" style="text-align: center">
<div class="content">
<a class="image" href="images/net-latency.png"><img src="images/net-latency.png" alt="Net Latency" width="650"></a>
</div>
<div class="title">Figure 16. Doge trades off CPU for Latency for better responsivity and to leave the service available to his friends</div>
</div>
<div class="paragraph">
<p>Blocking Read or Write become more like a nightmare for concurrent services use over long-living connections such as TCP or WebSocket. Apart from network routing component which might timeout a too long connection, little can be done with a blocking socket in the application locking the thread on read or write IO methods.</p>
</div>
<div class="paragraph">
<p>Of course there is always the choice to provide for a pool of threads or any <em>Async Facade</em> such as a <strong>Core Processor</strong> to mitigate the blocking read/write contention. The problem is there won&#8217;t be many of these threads available in a <strong>Reactive</strong> world of non blocking dispatching, so blocking behind 4/8/16 async facades is a limited option. Again the thread pool with a large queue or even many threads won&#8217;t necessarely solve the situation neither.</p>
</div>
<div class="paragraph">
<div class="title">Instead why not invoking callbacks on different IO operations: <em>connection, read, write, close&#8230;&#8203;</em> ?</div>
<p><strong>Reactor Net</strong> aims to provide an <strong>Asynchronous IO</strong> runtime that supports <strong>Reactive Streams</strong> backpressure for client or server needs over a range of protocols and drivers. Some drivers will not implement every protocol but at least one, <strong>Netty</strong>, implements all current protocols. At the moment, Reactor Net is  <strong>supporting Netty 4.x</strong> and <strong>ZeroMQ</strong> through <strong>jeroMQ 0.3.+</strong> and you must add explicitely one of them in the application classpath.</p>
</div>
<div class="paragraph">
<p><strong>Reactor Net</strong> has the following artifacts:</p>
</div>
<div class="sidebarblock">
<div class="content">
<div class="ulist">
<ul>
<li>
<p><code>ReactorChannel</code> and its direct implementations <code>ChannelStream</code> and <code>HttpChannel</code></p>
<div class="ulist">
<ul>
<li>
<p>Represents a direct connection between the application and the remote host</p>
</li>
<li>
<p>Contains non blocking IO write and read operations</p>
</li>
<li>
<p>Reactor drivers will directly expose <code>ChannelStream</code> to access the <code>Stream</code> functional API for read operations</p>
</li>
</ul>
</div>
</li>
<li>
<p><code>ReactorPeer</code> and <code>ReactorChannelHandler</code> for common network component (client/server) contract</p>
<div class="ulist">
<ul>
<li>
<p>Provides for <code>start</code> and <code>shutdown</code> operations</p>
</li>
<li>
<p>Binds a <code>ReactorChannelHandler</code> on <code>start</code> to listen to the requesting <code>ChannelStream</code></p>
</li>
<li>
<p><code>ReactorChannelHandler</code> is a function accepting <code>ChannelStream</code> requests and returning a <code>Publisher</code> for connection close management</p>
</li>
</ul>
</div>
</li>
<li>
<p><code>ReactorClient</code> for common client contract</p>
<div class="ulist">
<ul>
<li>
<p>Extends <code>ReactorPeer</code> to provide a <em>reconnect</em> friendly start operation</p>
</li>
</ul>
</div>
</li>
<li>
<p><code>NetStreams</code> and <code>Spec</code> to create any client or server</p>
<div class="ulist">
<ul>
<li>
<p>Looks like <code>Streams</code>, <code>BiStreams</code> and other <code>Reactor Stream</code> Factories</p>
</li>
<li>
<p><code>NetStreams</code> factories will accept <code>Function&lt;Spec,Spec&gt;</code> called <strong>once</strong> on creation to customize the configuration of the network component.</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>HTTP/WS/UDP/TCP</strong> protocol <code>ReactorPeer</code> implementations</p>
<div class="ulist">
<ul>
<li>
<p><code>HttpServer</code> &amp; <code>HttpClient</code> will provide routing extensions</p>
</li>
<li>
<p><code>DatagramServer</code> will provide multicast extensions</p>
</li>
<li>
<p><code>TcpServer</code> &amp; <code>TcpClient</code> will provide additional TCP/IP context informations</p>
</li>
</ul>
</div>
</li>
<li>
<p><strong>Netty</strong> and <strong>ZeroMQ</strong> drivers</p>
</li>
</ul>
</div>
</div>
</div>
<div class="admonitionblock note">
<table>
<tr>
<td class="icon">
<i class="fa icon-note" title="Note"></i>
</td>
<td class="content">
<strong>Reactor Net</strong> implements a model discussed under the <a href="https://github.com/reactive-ipc/reactive-ipc-jvm">Reactive IPC</a> initiative. As we progress we will align more and eventually depend on the specified artefacts likely over 2016. We give you a chance to experiment as of today with some of the principles and make our best to prepare our users to this next-generation standard.
</td>
</tr>
</table>
</div>
</div>
<div class="sect2">
<h3 id="_channels">Channels</h3>

</div>
<div class="sect2">
<h3 id="_channel_handlers">Channel Handlers</h3>

</div>
<div class="sect2">
<h3 id="_specifications">Specifications</h3>

</div>
<div class="sect2">
<h3 id="_client_specification">Client Specification</h3>

</div>
<div class="sect2">
<h3 id="_server_specification">Server Specification</h3>

</div>
<div class="sect2">
<h3 id="net-backpressure">Backpressure</h3>
<div class="paragraph">
<p>Using Reactor and Reactive Stream standard for flow-control with TCP network peers.</p>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="net-tcp101">TCP 101</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Using Reactor&#8217;s TCP support to create high-performance TCP clients and servers.</p>
</div>
<div class="sect2">
<h3 id="_start_and_stop">Start and Stop</h3>

</div>
<div class="sect2">
<h3 id="_writing_data">Writing Data</h3>
<div class="sect3">
<h4 id="_from_a_server_perspective">From a Server perspective</h4>

</div>
<div class="sect3">
<h4 id="_from_a_client_perspective">From a Client perspective</h4>

</div>
</div>
<div class="sect2">
<h3 id="_flushing_strategies">Flushing Strategies</h3>

</div>
<div class="sect2">
<h3 id="_consuming_data">Consuming Data</h3>
<div class="sect3">
<h4 id="_from_a_server_perspective_2">From a Server perspective</h4>

</div>
<div class="sect3">
<h4 id="_from_a_client_perspective_2">From a Client perspective</h4>

</div>
</div>
<div class="sect2">
<h3 id="_backpressure_strategies">Backpressure Strategies</h3>

</div>
<div class="sect2">
<h3 id="_closing_the_channel">Closing the Channel</h3>

</div>
</div>
</div>
<div class="sect1">
<h2 id="net-http101">HTTP 101</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Using Reactor&#8217;s HTTP support to create high-performance HTTP clients and servers.</p>
</div>
<div class="sect2">
<h3 id="_start_and_stop_2">Start and Stop</h3>

</div>
<div class="sect2">
<h3 id="_routing_http">Routing HTTP</h3>
<div class="sect3">
<h4 id="_sse">SSE</h4>

</div>
</div>
<div class="sect2">
<h3 id="_routing_websocket">Routing WebSocket</h3>

</div>
<div class="sect2">
<h3 id="_writing_data_2">Writing Data</h3>
<div class="sect3">
<h4 id="_adding_headers_and_other_metadata">Adding Headers and other Metadata</h4>

</div>
<div class="sect3">
<h4 id="_from_a_server_perspective_3">From a Server perspective</h4>

</div>
<div class="sect3">
<h4 id="_from_a_client_perspective_3">From a Client perspective</h4>

</div>
</div>
<div class="sect2">
<h3 id="_flushing_strategies_2">Flushing Strategies</h3>

</div>
<div class="sect2">
<h3 id="_consuming_data_2">Consuming Data</h3>
<div class="sect3">
<h4 id="_reading_headers_uri_params_and_other_metadata">Reading Headers, URI Params and other Metadata</h4>

</div>
<div class="sect3">
<h4 id="_from_a_server_perspective_4">From a Server perspective</h4>

</div>
<div class="sect3">
<h4 id="_from_a_client_perspective_4">From a Client perspective</h4>

</div>
</div>
<div class="sect2">
<h3 id="_backpressure_strategies_2">Backpressure Strategies</h3>

</div>
<div class="sect2">
<h3 id="_closing_the_channel_2">Closing the Channel</h3>

</div>
</div>
</div>
<div class="sect1">
<h2 id="net-endToEnd">End To End</h2>
<div class="sectionbody">
<div class="paragraph">
<p>Combining Reactor Net, Stream and Core to create standalone Ingesters or Data (micro)Services</p>
</div>
</div>
</div>
<h1 id="reactor-extensions" class="sect0"><strong>Extensions</strong></h1>
<div class="sect1">
<h2 id="reactor-spring">Spring Support</h2>
<div class="sectionbody">
<div class="sect2">
<h3 id="_spring_ecosystem_support">Spring Ecosystem Support</h3>
<div class="paragraph">
<p>Writing Reactor applications that are deployed inside a Spring <code>ApplicationContext</code>.</p>
</div>
</div>
<div class="sect2">
<h3 id="spring-basics">Spring Core Basics</h3>
<div class="paragraph">
<p>Writing Reactor applications that are deployed inside a Spring <code>ApplicationContext</code>.
TODO:</p>
</div>
</div>
<div class="sect2">
<h3 id="spring-boot">Reactor with Spring Boot</h3>

</div>
<div class="sect2">
<h3 id="spring-integration">Reactor with Spring Messaging</h3>
<div class="paragraph">
<p>Reactor is abstracted under the Spring Messaging <a href="https://docs.spring.io/spring/docs/current/spring-framework-reference/html/websocket.html">TCP support</a>.
Just make sure both Reactor Net <strong>io.projectreactor:reactor-net::2.0.8.BUILD-SNAPSHOT</strong> is in the Spring application classpath.</p>
</div>
</div>
<div class="sect2">
<h3 id="spring-integration-messaging">Reactor with Spring Integration</h3>

</div>
<div class="sect2">
<h3 id="_spring_integration_java_dsl">Spring Integration Java DSL</h3>

</div>
</div>
</div>
<div class="sect1">
<h2 id="spring-xd">Reactor with Spring XD</h2>
<div class="sectionbody">

</div>
</div>
<div class="sect1">
<h2 id="_groovy_extensions">Groovy extensions</h2>
<div class="sectionbody">
<div class="sect2">
<h3 id="_groovy_support">Groovy support</h3>

</div>
<div class="sect2">
<h3 id="_grails_support">Grails support</h3>
<div class="paragraph">
<p>Reactor is provided in core Grails 3.0 distribution as part of the <a href="https://grails.github.io/grails-doc/3.0.x/guide/single.html#events">Eventing support</a>.</p>
</div>
</div>
</div>
</div>
<div class="sect1">
<h2 id="clojure">Clojure support</h2>
<div class="sectionbody">
<div class="quoteblock">
<blockquote>
Meltdown is a Clojure interface to Reactor, an asynchronous programming, event passing and stream processing toolkit for the JVM.
It follows the path of Romulan, an old ClojureWerkz project on top of LMAX Disruptor that&#8217;s been abandoned.
</blockquote>
<div class="attribution">
&#8212; README<br>
<cite>project page</cite>
</div>
</div>
<div class="paragraph">
<p><a href="https://github.com/clojurewerkz/meltdown">ClojureWerkz Meltdown</a></p>
</div>
</div>
</div>
<div class="sect1">
<h2 id="reactor-samples">Cookbook</h2>
<div class="sectionbody">
<div class="sect2">
<h3 id="recipe-filestream">Building a simple File Stream</h3>
<div class="paragraph">
<p>Let&#8217;s start with a pure <code>Publisher</code> implementation, we&#8217;ll use Reactor API afterwads to simplify the following example.
As <code>Publisher</code> you will have to take care about a lot of small things that should be tested against the <strong>Reactive Streams</strong> TCK module. The purpose is to understand what <strong>Reactor</strong> can do for you in such situation to avoid all this machinery.</p>
</div>
<div class="admonitionblock important">
<table>
<tr>
<td class="icon">
<i class="fa icon-important" title="Important"></i>
</td>
<td class="content">
In theory, <strong>Reactive Streams</strong> won&#8217;t buy you much in a scenario of File Read blocking consuming, single threaded, over a simple loop doing that. If the <em>sink</em> endpoint is blocking you already have a form of backpressure since it won&#8217;t read more than it sends. The point of such Reactive File Stream is when in between it and the consumer there is one or more boundaries to cross, a decoupling that can take the form of a queue or a ring buffer. You could envision this scenario where you want to keep reading while the consumer is sending so the next time it asks for data (after sending its previous one), the data <strong>is already in-memory</strong>. A sort of prefetching in other words.
</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Build a lazy file read Publisher matching the Subscriber request</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java">  Publisher&lt;<span class="predefined-type">String</span>&gt; fileStream = <span class="keyword">new</span> Publisher&lt;<span class="predefined-type">String</span>&gt;() { <i class="conum" data-value="1"></i><b>(1)</b>
          <span class="annotation">@Override</span>
          <span class="directive">public</span> <span class="type">void</span> subscribe(<span class="directive">final</span> Subscriber&lt;? <span class="local-variable">super</span> <span class="predefined-type">String</span>&gt; subscriber) {
                  <span class="directive">final</span> <span class="predefined-type">File</span> file = <span class="keyword">new</span> <span class="predefined-type">File</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">settings.gradle</span><span class="delimiter">&quot;</span></span>); <i class="conum" data-value="2"></i><b>(2)</b>
  
                  <span class="keyword">try</span> {
                          <span class="directive">final</span> <span class="predefined-type">BufferedReader</span> is = <span class="keyword">new</span> <span class="predefined-type">BufferedReader</span>(<span class="keyword">new</span> <span class="predefined-type">FileReader</span>(file)); <i class="conum" data-value="2"></i><b>(2)</b>
  
                          subscriber.onSubscribe(<span class="keyword">new</span> Subscription() {
  
                                  <span class="directive">final</span> <span class="predefined-type">AtomicBoolean</span> terminated = <span class="keyword">new</span> <span class="predefined-type">AtomicBoolean</span>(<span class="predefined-constant">false</span>);
  
                                  <span class="annotation">@Override</span>
                                  <span class="directive">public</span> <span class="type">void</span> request(<span class="type">long</span> n) {
                                          <span class="type">long</span> requestCursor = <span class="integer">0l</span>;
                                          <span class="keyword">try</span> {
                                                  <span class="predefined-type">String</span> line;
                                                  <span class="keyword">while</span> ((requestCursor++ &lt; n || n == <span class="predefined-type">Long</span>.MAX_VALUE) <i class="conum" data-value="3"></i><b>(3)</b>
                                                                  &amp;&amp; !terminated.get()) { <i class="conum" data-value="4"></i><b>(4)</b>
  
                                                          line = is.readLine();
                                                          <span class="keyword">if</span> (line != <span class="predefined-constant">null</span>) {
                                                                  subscriber.onNext(line);
                                                          } <span class="keyword">else</span> {
                                                                  <span class="keyword">if</span> (terminate()) {
                                                                          subscriber.onComplete(); <i class="conum" data-value="5"></i><b>(5)</b>
                                                                  }
                                                                  <span class="keyword">return</span>;
                                                          }
                                                  }
                                          } <span class="keyword">catch</span> (<span class="exception">IOException</span> e) {
                                                  <span class="keyword">if</span> (terminate()) {
                                                          subscriber.onError(e); <i class="conum" data-value="6"></i><b>(6)</b>
                                                  }
                                          }
                                  }
  
                                  <span class="annotation">@Override</span>
                                  <span class="directive">public</span> <span class="type">void</span> cancel() {
                                          terminate();
                                  }
  
                                  <span class="directive">private</span> <span class="type">boolean</span> terminate() {
                                          <span class="keyword">if</span> (terminated.compareAndSet(<span class="predefined-constant">false</span>, <span class="predefined-constant">true</span>)) {
                                                  <span class="keyword">try</span> {
                                                          is.close(); <i class="conum" data-value="7"></i><b>(7)</b>
                                                  } <span class="keyword">catch</span> (<span class="exception">Exception</span> t) {
                                                          subscriber.onError(t);
                                                  }
                                                  <span class="keyword">return</span> <span class="predefined-constant">true</span>;
                                          }
                                          <span class="keyword">return</span> <span class="predefined-constant">false</span>;
                                  }
                          });
  
                  } <span class="keyword">catch</span> (<span class="exception">FileNotFoundException</span> e) {
                          Streams.&lt;<span class="predefined-type">String</span>, <span class="exception">FileNotFoundException</span>&gt; fail(e)
                                  .subscribe(subscriber); <i class="conum" data-value="8"></i><b>(8)</b>
                  }
          }
  };
  
  Streams.wrap(fileStream)
          .capacity(<span class="integer">4L</span>) <i class="conum" data-value="9"></i><b>(9)</b>
          .consumeOn( <i class="conum" data-value="10"></i><b>(10)</b>
                  Environment.sharedDispatcher(),
                  <span class="predefined-type">System</span>.out::println,
                  <span class="predefined-type">Throwable</span>::printStackTrace,
                  nothing -&gt; <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">## EOF ##</span><span class="delimiter">&quot;</span></span>)
  );</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Implement a <code>Publisher</code>. We&#8217;ll see in the next example how to be smart about it with core and stream</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Open a <code>File</code> cursor and reader by Subscriber to allow for replayability: It&#8217;s a <code>Cold Stream</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Match the number of read lines with the demand and ignore the demand if special Long.MAX_VALUE escaping number is passed.</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Check before each possible <code>onNext()</code> if the Stream is not <strong>cancelled</strong>.</td>
</tr>
<tr>
<td><i class="conum" data-value="5"></i><b>5</b></td>
<td>Call <code>onComplete()</code> which set the state of the <code>Subscription</code> to <strong>cancelled</strong>, ignoring further terminal signal if any.</td>
</tr>
<tr>
<td><i class="conum" data-value="6"></i><b>6</b></td>
<td>Call <code>onError(e)</code> which set the state of the <code>Subscription</code> to <strong>cancelled</strong>, ignoring further terminal signal if any.</td>
</tr>
<tr>
<td><i class="conum" data-value="7"></i><b>7</b></td>
<td>Close the file if the subscriber is not interested any more in the content (error, completion, cancel).</td>
</tr>
<tr>
<td><i class="conum" data-value="8"></i><b>8</b></td>
<td>Create a failed <code>Stream</code> that only <code>onSubscribe()</code> the pass subscriber and <code>onError(e)</code> it.</td>
</tr>
<tr>
<td><i class="conum" data-value="9"></i><b>9</b></td>
<td><code>capacity</code> will hint downstream operations (<code>consumeOn</code> here) to chunk requests 4 by 4.</td>
</tr>
<tr>
<td><i class="conum" data-value="10"></i><b>10</b></td>
<td><code>consumeOn</code> takes an extra argument to run the requests on a dispatcher in addition to the 3 possible <code>Consumer</code> reacting to each type of signal.</td>
</tr>
</table>
</div>
<div class="listingblock">
<div class="title">Build a lazy file read with Core PublisherFactory§ (from 2.0.2+) and compose with Stream API</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="directive">final</span> <span class="predefined-type">String</span> filename = <span class="string"><span class="delimiter">&quot;</span><span class="content">settings.gradle</span><span class="delimiter">&quot;</span></span>;
Publisher&lt;<span class="predefined-type">String</span>&gt; fileStream = PublisherFactory.create(
        (n, sub) -&gt; { <i class="conum" data-value="1"></i><b>(1)</b>
                <span class="predefined-type">String</span> line;
                <span class="directive">final</span> <span class="predefined-type">BufferedReader</span> inputStream = sub.context() <i class="conum" data-value="2"></i><b>(2)</b>
                <span class="type">long</span> requestCursor = <span class="integer">0l</span>;
                <span class="keyword">while</span> ((requestCursor++ &lt; n || n == <span class="predefined-type">Long</span>.MAX_VALUE) &amp;&amp; !sub.isCancelled()) { <i class="conum" data-value="3"></i><b>(3)</b>

                        <span class="keyword">try</span> {
                                line = inputStream.readLine();
                                <span class="keyword">if</span> (line != <span class="predefined-constant">null</span>) {
                                        sub.onNext(line);
                                } <span class="keyword">else</span> {
                                        sub.onComplete(); <i class="conum" data-value="4"></i><b>(4)</b>
                                        <span class="keyword">return</span>;
                                }
                        }
                        <span class="keyword">catch</span> (<span class="exception">IOException</span> exc) {
                                sub.onError(exc);
                        }
                }
        },
        sub -&gt; <span class="keyword">new</span> <span class="predefined-type">BufferedReader</span>(<span class="keyword">new</span> <span class="predefined-type">FileReader</span>(filename)), <i class="conum" data-value="5"></i><b>(5)</b>
        inputStream -&gt; inputStream.close() <i class="conum" data-value="6"></i><b>(6)</b>
);

Streams
        .wrap(fileStream)
        .process(RingBufferProcessor.create())
        .capacity(<span class="integer">4L</span>)
        .consume(
                <span class="predefined-type">System</span>.out::println,
                <span class="predefined-type">Throwable</span>::printStackTrace,
                nothing -&gt; <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">## EOF ##</span><span class="delimiter">&quot;</span></span>)
);</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Implement a <code>BiConsumer</code> to react on every <code>Subscriber</code> request <code>Long</code> n. Any unchecked exception will trigger the terminal callback and <code>Subscriber.onError(e)</code>.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>The <code>Subscriber</code> passed in the callback is a <code>SubscriberWithContext</code> decorator allowing access to <code>context()</code>  populated on start</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Match the number of read lines with the demand and ignore the demand if special Long.MAX_VALUE escaping number is passed. Also use <code>SubscriberWithContext.isCancelled()</code> to check asynchronous cancel from <code>Subscribers</code> before each read.</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Call <code>onComplete()</code> which set the state of the <code>SubscriberWithContext</code> to <strong>cancelled</strong>, ignoring further terminal signal if any.</td>
</tr>
<tr>
<td><i class="conum" data-value="5"></i><b>5</b></td>
<td>Define a context once for a new <code>Subscriber</code> that will be available later for each request <code>SubscriberWithContext.context()</code></td>
</tr>
<tr>
<td><i class="conum" data-value="6"></i><b>6</b></td>
<td>Define a terminal callback once intercepting <code>cancel()</code>, <code>onComplete()</code> or <code>onError(e)</code>.</td>
</tr>
</table>
</div>
<div class="paragraph">
<p>We can use <code>PublisherFactory</code>, or <a href="#streams-basics">Streams factories</a> like <code>Streams.createWith()</code> to quickly achieve common use cases:</p>
</div>
<div class="ulist">
<ul>
<li>
<p>Open IO once</p>
</li>
<li>
<p>React on requests</p>
</li>
<li>
<p>Handle shutdown gracefully</p>
</li>
</ul>
</div>
</div>
<div class="sect2">
<h3 id="recipes-circuitbreaker">Building a Quick Circuit Breaker</h3>
<div class="paragraph">
<p>In this other exercise, we will focus more on the composition power in your hands with <strong>Reactor Stream</strong> module. A classic use-case is to build self-healing data pipelines using the <a href="https://martinfowler.com/bliki/CircuitBreaker.html">Circuit Breaker Pattern</a> (maybe soon available in <code>Stream</code> API, maybe).</p>
</div>
<div class="paragraph">
<p>In this scenario, we want to keep alive a <code>Stream</code> even if errors might fly in. When a certain number of errors is reached, we want to stop consuming from the main <em>circuit</em>, the actual <code>Stream</code>. For a short period we will <em>trip</em> the circuit and use a fallback publisher <code>Stream</code>. This fallback can actually be any sort of <code>Publisher</code>, we will just emit an alternative message. The point is to avoid new access to the failing <code>Stream</code> for a while and give it a chance to recover.</p>
</div>
<div class="listingblock">
<div class="title">Quick (and dirty) Circuit Breaker test</div>
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="directive">final</span> Broadcaster&lt;<span class="predefined-type">String</span>&gt; closeCircuit = Broadcaster.create(); <i class="conum" data-value="1"></i><b>(1)</b>
<span class="directive">final</span> Stream&lt;<span class="predefined-type">String</span>&gt; openCircuit = Streams.just(<span class="string"><span class="delimiter">&quot;</span><span class="content">Alternative Message</span><span class="delimiter">&quot;</span></span>); <i class="conum" data-value="2"></i><b>(2)</b>

<span class="directive">final</span> <span class="predefined-type">Action</span>&lt;Publisher&lt;? <span class="directive">extends</span> <span class="predefined-type">String</span>&gt;, <span class="predefined-type">String</span>&gt; circuitSwitcher = Streams.switchOnNext(); <i class="conum" data-value="3"></i><b>(3)</b>

<span class="directive">final</span> <span class="predefined-type">AtomicInteger</span> successes = <span class="keyword">new</span> <span class="predefined-type">AtomicInteger</span>(); <i class="conum" data-value="4"></i><b>(4)</b>
<span class="directive">final</span> <span class="predefined-type">AtomicInteger</span> failures = <span class="keyword">new</span> <span class="predefined-type">AtomicInteger</span>();

<span class="directive">final</span> <span class="type">int</span> maxErrors = <span class="integer">3</span>;

Promise&lt;<span class="predefined-type">List</span>&lt;<span class="predefined-type">String</span>&gt;&gt; promise = <i class="conum" data-value="5"></i><b>(5)</b>
                circuitSwitcher <i class="conum" data-value="6"></i><b>(6)</b>
                        .observe(d -&gt; successes.incrementAndGet()) <i class="conum" data-value="7"></i><b>(7)</b>
                        .when(<span class="predefined-type">Throwable</span>.class, error -&gt; failures.incrementAndGet())
                        .observeStart(s -&gt; { <i class="conum" data-value="8"></i><b>(8)</b>

                                <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">failures: </span><span class="delimiter">&quot;</span></span> + failures +
                                         <span class="string"><span class="delimiter">&quot;</span><span class="content"> successes:</span><span class="delimiter">&quot;</span></span> + successes);

                                <span class="keyword">if</span> (failures.compareAndSet(maxErrors, <span class="integer">0</span>)) {
                                        circuitSwitcher.onNext(openCircuit); <i class="conum" data-value="9"></i><b>(9)</b>
                                        successes.set(<span class="integer">0</span>);

                                        Streams
                                                .timer(<span class="integer">1</span>)  <i class="conum" data-value="10"></i><b>(10)</b>
                                                .consume(ignore -&gt; circuitSwitcher.onNext(closeCircuit));
                                }
                        })
                        .retry() <i class="conum" data-value="11"></i><b>(11)</b>
                        .toList(); <i class="conum" data-value="5"></i><b>(5)</b>

circuitSwitcher.onNext(closeCircuit); <i class="conum" data-value="12"></i><b>(12)</b>

closeCircuit.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">test1</span><span class="delimiter">&quot;</span></span>);
closeCircuit.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">test2</span><span class="delimiter">&quot;</span></span>);
closeCircuit.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">test3</span><span class="delimiter">&quot;</span></span>);
closeCircuit.onError(<span class="keyword">new</span> <span class="exception">Exception</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">test4</span><span class="delimiter">&quot;</span></span>));
closeCircuit.onError(<span class="keyword">new</span> <span class="exception">Exception</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">test5</span><span class="delimiter">&quot;</span></span>));
closeCircuit.onError(<span class="keyword">new</span> <span class="exception">Exception</span>(<span class="string"><span class="delimiter">&quot;</span><span class="content">test6</span><span class="delimiter">&quot;</span></span>));
<span class="predefined-type">Thread</span>.sleep(<span class="integer">1500</span>); <i class="conum" data-value="13"></i><b>(13)</b>
closeCircuit.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">test7</span><span class="delimiter">&quot;</span></span>);
closeCircuit.onNext(<span class="string"><span class="delimiter">&quot;</span><span class="content">test8</span><span class="delimiter">&quot;</span></span>);
closeCircuit.onComplete();  <i class="conum" data-value="14"></i><b>(14)</b>
circuitSwitcher.onComplete();

<span class="predefined-type">System</span>.out.println(promise.await());
Assert.assertEquals(promise.get().get(<span class="integer">0</span>), <span class="string"><span class="delimiter">&quot;</span><span class="content">test1</span><span class="delimiter">&quot;</span></span>);
Assert.assertEquals(promise.get().get(<span class="integer">1</span>), <span class="string"><span class="delimiter">&quot;</span><span class="content">test2</span><span class="delimiter">&quot;</span></span>);
Assert.assertEquals(promise.get().get(<span class="integer">2</span>), <span class="string"><span class="delimiter">&quot;</span><span class="content">test3</span><span class="delimiter">&quot;</span></span>);
Assert.assertEquals(promise.get().get(<span class="integer">3</span>), <span class="string"><span class="delimiter">&quot;</span><span class="content">Alternative Message</span><span class="delimiter">&quot;</span></span>);
Assert.assertEquals(promise.get().get(<span class="integer">4</span>), <span class="string"><span class="delimiter">&quot;</span><span class="content">test7</span><span class="delimiter">&quot;</span></span>);
Assert.assertEquals(promise.get().get(<span class="integer">5</span>), <span class="string"><span class="delimiter">&quot;</span><span class="content">test8</span><span class="delimiter">&quot;</span></span>);</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Create the main <strong>hot</strong> <code>Broadcaster</code> stream to send data later on.</td>
</tr>
<tr>
<td><i class="conum" data-value="2"></i><b>2</b></td>
<td>Create a simple fallback stream when sh*t hits the fan.</td>
</tr>
<tr>
<td><i class="conum" data-value="3"></i><b>3</b></td>
<td>Create a <code>SwitchAction</code> which is a <code>Processor</code> accepting new <code>Publisher</code> to consume data from.</td>
</tr>
<tr>
<td><i class="conum" data-value="4"></i><b>4</b></td>
<td>Prepare shared counters for successes and failures.</td>
</tr>
<tr>
<td><i class="conum" data-value="5"></i><b>5</b></td>
<td>Return a <code>Promise</code> from <code>Stream.toList()</code> to convert the <code>Stream</code> into an eventual <code>List</code></td>
</tr>
<tr>
<td><i class="conum" data-value="6"></i><b>6</b></td>
<td>Consume data from the circuitSwitcher <code>Processor</code> proxy that will be updated depending on the failures number.</td>
</tr>
<tr>
<td><i class="conum" data-value="7"></i><b>7</b></td>
<td>Count success on every valid <code>onNext(String)</code> and count errors on every <code>Throwable</code> exception</td>
</tr>
<tr>
<td><i class="conum" data-value="8"></i><b>8</b></td>
<td>Monitor <code>onSubscribe(Subscription)</code> call which is called after successful stream start.</td>
</tr>
<tr>
<td><i class="conum" data-value="9"></i><b>9</b></td>
<td>If the number of error is <em>maxErrors</em>, trip the circuit by changing the current circuitSwitcher data source to the fallback one.</td>
</tr>
<tr>
<td><i class="conum" data-value="10"></i><b>10</b></td>
<td>Re-consume from the main stream in 1 Second by signalling circuitSwitcher with it.</td>
</tr>
<tr>
<td><i class="conum" data-value="11"></i><b>11</b></td>
<td>Keep retrying on any exception, which means Cancel / Re Subscribe. That&#8217;s why we <code>observeStart()</code> as any error will trigger it.</td>
</tr>
<tr>
<td><i class="conum" data-value="12"></i><b>12</b></td>
<td>Start the circuitSwitcher with the main <code>Stream</code></td>
</tr>
<tr>
<td><i class="conum" data-value="13"></i><b>13</b></td>
<td>Artificial wait to leave a chance to the timer to close the circuit,</td>
</tr>
<tr>
<td><i class="conum" data-value="14"></i><b>14</b></td>
<td>Double <code>onComplete()</code> the current main stream and the circuitSwitcher itself (otherwise they will hang for the missing <code>onComplete()</code>.</td>
</tr>
</table>
</div>
</div>
<div class="sect2">
<h3 id="_building_efficient_data_pipelines">Building Efficient Data Pipelines</h3>

</div>
<div class="sect2">
<h3 id="_building_non_blocking_microservices">Building Non-Blocking MicroServices</h3>

</div>
<div class="sect2">
<h3 id="_building_cqrs_like_applications">Building CQRS-like Applications</h3>

</div>
<div class="sect2">
<h3 id="_other_example_applications">Other Example Applications</h3>
<div class="hdlist">
<table>
<tr>
<td class="hdlist1">
<a href="https://github.com/reactor/reactor-quickstart">Quickstart</a>
</td>
<td class="hdlist2">
<p>An example application showing several ways to use basic components in Reactor.</p>
</td>
</tr>
<tr>
<td class="hdlist1">
<a href="https://github.com/reactor/reactor-samples">Samples</a>
</td>
<td class="hdlist2">
<p>A simple sample application that demonstrates Reactor functionality in JUnit tests.</p>
</td>
</tr>
</table>
</div>
<h4 id="_non_blocking_konami_code" class="discrete">Non Blocking Konami Code</h4>
<div class="paragraph">
<p>If you made it that far, here a simple non blocking stream to scale up your Konami codes over websocket. Tell me about a reward&#8230;&#8203; Don&#8217;t forget to add <strong>Netty</strong> in your classpath along <strong>reactor-net</strong>.</p>
</div>
<div class="listingblock">
<div class="content">
<pre class="CodeRay highlight"><code data-lang="java"><span class="directive">final</span> Processor&lt;<span class="predefined-type">Integer</span>, <span class="predefined-type">Integer</span>&gt; keyboardStream = RingBufferProcessor.create();

NetStreams.&lt;<span class="predefined-type">String</span>, <span class="predefined-type">String</span>&gt;httpServer(spec -&gt;
                spec
                        .codec(StandardCodecs.STRING_CODEC)
                        .listen(<span class="integer">3000</span>)
        )
        .ws(<span class="string"><span class="delimiter">&quot;</span><span class="content">/</span><span class="delimiter">&quot;</span></span>, channel -&gt; {
                <span class="predefined-type">System</span>.out.println(<span class="string"><span class="delimiter">&quot;</span><span class="content">Connected a websocket client: </span><span class="delimiter">&quot;</span></span> + channel.remoteAddress());

                <span class="keyword">return</span> Streams
                        .wrap(keyboardStream)
                        .skipWhile(key -&gt; <span class="predefined-type">KeyEvent</span>.VK_UP != key)
                        .buffer(<span class="integer">10</span>, <span class="integer">1</span>) <i class="conum" data-value="1"></i><b>(1)</b>
                        .map(keys -&gt; keys.size() == <span class="integer">10</span> &amp;&amp;
                                keys.get(<span class="integer">0</span>) == <span class="predefined-type">KeyEvent</span>.VK_UP &amp;&amp;
                                keys.get(<span class="integer">1</span>) == <span class="predefined-type">KeyEvent</span>.VK_UP &amp;&amp;
                                keys.get(<span class="integer">2</span>) == <span class="predefined-type">KeyEvent</span>.VK_DOWN &amp;&amp;
                                keys.get(<span class="integer">3</span>) == <span class="predefined-type">KeyEvent</span>.VK_DOWN &amp;&amp;
                                keys.get(<span class="integer">4</span>) == <span class="predefined-type">KeyEvent</span>.VK_LEFT &amp;&amp;
                                keys.get(<span class="integer">5</span>) == <span class="predefined-type">KeyEvent</span>.VK_RIGHT &amp;&amp;
                                keys.get(<span class="integer">6</span>) == <span class="predefined-type">KeyEvent</span>.VK_LEFT &amp;&amp;
                                keys.get(<span class="integer">7</span>) == <span class="predefined-type">KeyEvent</span>.VK_RIGHT &amp;&amp;
                                keys.get(<span class="integer">8</span>) == <span class="predefined-type">KeyEvent</span>.VK_B &amp;&amp;
                                keys.get(<span class="integer">9</span>) == <span class="predefined-type">KeyEvent</span>.VK_A
                )
                .map(isKonami -&gt; isKonami ? <span class="string"><span class="delimiter">&quot;</span><span class="content">Konami!</span><span class="delimiter">&quot;</span></span> : <span class="string"><span class="delimiter">&quot;</span><span class="content">Nah</span><span class="delimiter">&quot;</span></span>)
                .nest()
                .flatMap(konamis -&gt;
                        channel.writeWith(konamis)
                );
        })
        .start()
        .await();

keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_RIGHT);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_UP);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_UP);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_DOWN);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_DOWN);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_LEFT);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_RIGHT);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_LEFT);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_RIGHT);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_B);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_A);
keyboardStream.onNext(<span class="predefined-type">KeyEvent</span>.VK_C);
keyboardStream.onComplete();

<span class="predefined-type">System</span>.out.println(konamis.await());</code></pre>
</div>
</div>
<div class="colist arabic">
<table>
<tr>
<td><i class="conum" data-value="1"></i><b>1</b></td>
<td>Note the <code>buffer(size, skip)</code> use, we want to evaluate all last 10 keys combinations, 10 by 10. That means we need to create a new list of 10 keys for every key.</td>
</tr>
</table>
</div>
</div>
</div>
</div>
</div>
<div id="footnotes">
<hr>
<div class="footnote" id="_footnote_1">
<a href="#_footnoteref_1">1</a>. Unless you only want to use the Core Processor which are mostly standalone at this stage. We plan to align Dispatcher with Core Processors overtime.
</div>
<div class="footnote" id="_footnote_2">
<a href="#_footnoteref_2">2</a>. Some will challenge that over-simplified vision but let&#8217;s stay pragmatic over here :)
</div>
<div class="footnote" id="_footnote_3">
<a href="#_footnoteref_3">3</a>. including <a href="https://akka.io">Akka Streams</a>, <a href="https://ratpack.io">Ratpack</a>, and <a href="https://github.com/ReactiveX/RxJava">RxJava</a>
</div>
</div>
<div id="footer">
<div id="footer-text">
Last updated 2017-04-21 13:09:01 BST
</div>
</div>
</body>
</html>